Ok, sau khoảng hai giờ mày mò tôi đã xoay sở để làm điều này nhưng nó đòi hỏi phải thêm một số cơ thể phụ. Bạn có thể muốn trích xuất nội dung này thành một phương thức / lớp nhưng ý tưởng cơ bản là:
Tạo những gì tôi gọi là cơ quan "chủ sở hữu" cho các đối tượng của bạn. Các cơ quan này chia sẻ kích thước và vị trí của các "đối tượng" của bạn nhưng không tham gia vào các vụ va chạm. Về cơ bản, chúng là bản sao.
//Create "Main" (center) body
_bodyMain = BodyFactory.CreateRectangle(World, 5f, 5f, 1f);
_bodyMain.BodyType = BodyType.Dynamic;
_bodyMain.Position = new Vector2(2, 2);
//Create "MainHolder"
_bodyMainHolder = BodyFactory.CreateRectangle(World, 5f, 5f, 1f);
_bodyMainHolder.BodyType = BodyType.Dynamic;
_bodyMainHolder.CollisionCategories = Category.None; //Prevents collisions
_bodyMainHolder.Position = new Vector2(2, 2);
_bodyMainHolder.IsSensor = true;
//See http://farseerphysics.codeplex.com/discussions/222524 for why they're sensors
_bodyMainHolder.FixedRotation = true;
//Note: Only add FixedRotation for the main one, leave it off of the other
// holders. I'll explain later.
Đính kèm mỗi người giữ vào "mainHolder" bằng cách sử dụng a WeldJoint
. Điều này sẽ ngăn họ di chuyển khỏi nhau. Trên FixedRotation
mainHolder ngăn chúng quay. Tôi không biết có lỗi trong trò hề hay không nhưng nếu bạn thêm một
WeldJoint
và cả hai cơ thể FixedRotation == true
thì khớp không hoạt động bình thường. Đây là lý do tại sao chỉ có chủ sở hữu chính có .FixedRotation = true
.
//Weld the holders together so they don't move. Assumes another holder is defined
// for the object on the right side (bodyRightHolder).
JointFactory.CreateWeldJoint(World, _bodyMainHolder, _bodyRightHolder,
_bodyRightHolder.Position - _bodyMainHolder.Position, Vector2.Zero);
Đính kèm các đối tượng "đối tượng" của bạn với chủ sở hữu tương ứng của họ bằng RevoluteJoint
s. Điều này khóa các đối tượng của bạn với chủ sở hữu nhưng cho phép chúng xoay tự do.
//Lock the actual bodies to the holders
JointFactory.CreateRevoluteJoint(World, _bodyMainHolder, _bodyMain, Vector2.Zero);
JointFactory.CreateRevoluteJoint(World, _bodyRightHolder, _bodyRight, Vector2.Zero);
Làm cho các vật thể thật của bạn xoay khớp với nhau bằng cách gắn một khớp góc. Lưu ý: bạn không phải gắn khớp góc với từng cặp đối tượng. Chỉ cần thêm một khớp góc vào thân chính và thân kia và các phép quay sẽ dịch trên tất cả các đối tượng.
//Make them rotate the same as each other
JointFactory.CreateAngleJoint(World, _bodyMain, _bodyRight);
Đó là nó! Chỉ cần thêm mã bổ sung cho từng đối tượng / đối tượng khác mà bạn muốn và nó sẽ xử lý phần còn lại. Đây là một hình ảnh để minh họa thử nghiệm của tôi:
Ở đây bạn sẽ thấy các cơ thể màu xanh lá cây là chủ sở hữu. Chúng không xoay hoặc va chạm và được hàn lại với nhau. Các cơ thể màu vàng và đỏ là "đối tượng" của bạn (màu vàng là chính). Bạn có thể thấy rằng chúng được xoay theo cùng một lượng và đang xoay quanh các chủ sở hữu tương ứng của chúng. Ngoài ra, chỉ có các cơ thể màu đỏ và màu vàng tham gia vào các vụ va chạm. Tôi tin rằng điều này đáp ứng cả ba điều kiện của bạn ở trên.
Ví dụ làm việc
Nếu bạn tải lên giải pháp "Samples XNA" của Farseer và tìm SimpleDemo1.cs (dự án "Samples XNA"> "Samples"), tôi sẽ viết lại ( mã ở đây ) để kiểm tra.
Hi vọng điêu nay co ich. Hãy cho tôi biết nếu bạn có bất kỳ câu hỏi.