2017-01-02 4 views
2

Ich versuche Kollisionsfilterung wie in der "Matter.js body documentation" beschrieben zu verwenden. Für mein Projekt muss ich jedoch Kollisionen zwischen verschiedenen Composite-Objekten deaktivieren. Es dürfen also nur Körper kollidieren, die sich im selben Verbund befinden. Ich habe vor, mehr als 32 Composites zu haben (32 ist die maximale Anzahl von Kollisionskategorien, die von Matter.js zur Verfügung gestellt werden). Wie würde ich das erreichen?Matter.js Kollision zwischen verschiedenen Composites deaktivieren

// module aliases 
var Engine = Matter.Engine, 
    Render = Matter.Render, 
    World = Matter.World, 
    Bodies = Matter.Bodies, 
    Body = Matter.Body, 
    Vector = Matter.Vector, 
    Composite = Matter.Composite, 
    Constraint = Matter.Constraint, 
    MouseConstraint = Matter.MouseConstraint; 

// create an engine 
var engine = Engine.create(); 

// create a renderer 
var container = document.getElementById("container"); 
var canvas = document.getElementById("maincanvas"); 

var render = Render.create({ 
    element: container, 
    canvas: canvas, 
    engine: engine, 
    options: { 
     height: 400, 
     width: 400, 
     wireframes: false 
    } 
}); 

// This makes collision much easier to test 
engine.world.gravity = {x:0, y:0}; 

// Add a mouseconstraint to test 
var mc = MouseConstraint.create(engine, { 
    element: render.canvas 
}); 
Composite.add(engine.world, mc); 

var bodies1 = [] 
var bodies2 = [] 
var xpos = 30 
var ypos = 30 
for (var i = 0; i < 5; i++){ 
    bodies1.push(Bodies.circle(xpos, ypos, 10, { 
     collisionFilter: { 
      group:-1 
     }, 
     render: { 
      fillStyle: "blue" 
     } 
    }) 
    ); 
    xpos += 30; 
} 
for (var i = 0; i < 5; i++){ 
    bodies2.push(Bodies.circle(xpos, ypos, 10, { 
     collisionFilter: { 
      group:-1 
     }, 
     render: { 
      fillStyle: "red" 
     } 
    }) 
    ); 
    xpos += 30; 
} 

var composite1 = Composite.create(); 
Composite.add(composite1, bodies1); 
var composite2 = Composite.create(); 
Composite.add(composite2, bodies2); 

Composite.add(engine.world, [composite1, composite2]); 

Engine.run(engine); 
Render.run(render); 

Auf diese Weise ich in der Lage bin Kollision zwischen den Kompositen zu deaktivieren, aber diese deaktiviert auch ‚von innen‘ die Verbund Kollision. Ich könnte dies mit dem collisionFilter.category System tun, aber wie würde das mit mehr als 32 Verbundwerkstoffen funktionieren?

Antwort

1

Es gibt keine Unterstützung für die Kollisionsfilterung auf der Composite-Ebene, Sie müssen damit auf Körperebene umgehen. Um dies einfacher zu verwalten, erstellen Sie einfach einige zusammengesetzte Hilfsfunktionen, z. compositeSetCollisionFilter(composite, filter) und iterieren über Composite.allBodies(composite).

In Bezug auf die Grenze von 32 Kategorien, ist dies aufgrund einer bitwise implementation (für die Leistung angeblich, obwohl ich bezweifle, dass es viel in der Realität wichtig ist). Ich habe ein Problem mit dem Projekt über reconsidering this angesprochen.

Für jetzt gibt es eine Möglichkeit, mehr zu haben, wenn Sie Matter.Detector.canCollide(filterA, filterB) durch Ihre eigene Funktion ersetzen, die zwei body.collisionFilter Objekte vergleichen kann. Mit diesem können Sie jedes Schema verwenden, das Sie für body.collisionFilter Objekte mögen.

Verwandte Themen