Nên phát hiện va chạm logic ở đâu?


19

Tôi đang phát triển một công cụ trò chơi 2D nhỏ. Các ký tự có một phương thức vẽ hiện đang làm như sau:

  1. Tính toán vị trí mới của nhân vật theo tốc độ của nó, v.v.
  2. Cập nhật ô lưới va chạm **
  3. Vẽ nhân vật ở vị trí mới

** Tôi đã tạo lưới va chạm để giảm số lần kiểm tra giao lộ

Bây giờ thuật toán cơ bản mà tôi đã nghĩ để phát hiện va chạm là:

For Each Character
    Check intersection with characters in surrounding 8 cells

Tôi chỉ có thể đặt mã này trong phương pháp sơn. Nhưng đây là vấn đề tôi dự đoán.

Giả sử hai ký tự A và B nằm trong các ô liền kề trong lưới va chạm. Bây giờ theo thuật toán trên trong lần lặp của ký tự A, nó sẽ phát hiện ra rằng nó đã va chạm với B. Trong lần lặp cho ký tự B, nó sẽ phát hiện ra rằng nó đã va chạm với A.

Nhưng tôi có một ý tưởng rằng khi A phát hiện ra rằng nó đã va chạm với B, nó nên thông báo cho B rằng nó đã va chạm với A. Điều này sẽ tiết kiệm rất nhiều so sánh khi có hơn 2 diễn viên va chạm. Nhưng tôi không chắc làm thế nào để xử lý việc này. Tôi nghĩ thay vì mỗi nhân vật kiểm tra sự va chạm của nó, tôi nên kiểm tra sự va chạm bên trong vòng lặp trò chơi.

Cách tiếp cận này sẽ đúng? Làm thế nào bạn đã xử lý loại vấn đề này? Tôi nghĩ về những điều lưới va chạm bản thân mình. Có bất kỳ sự thay thế cho logic lưới va chạm?


Tôi xin lỗi cho nitpick, nhưng trong một thư viện vật lý 2D chuyên biệt. Vật lý trò chơi thường rất gần đúng, vì vậy mọi giải pháp không làm cho trò chơi không thể chơi được là tốt, nhưng nếu bạn muốn giải quyết chính xác, chỉ cần sử dụng vật lý chuyên dụng như Box2D ... :-D
user712092

Câu trả lời:


14

Cách tiếp cận thông thường để phát hiện va chạm là không có A hoặc B tự phát hiện va chạm.

Thay vào đó, trước tiên, bạn di chuyển tất cả các đối tượng, sau đó có một hệ thống va chạm riêng để tìm sự va chạm giữa tất cả các cặp đối tượng, cho mọi đối tượng biết về những thứ mà nó đã va chạm, và cuối cùng kết xuất tất cả các đối tượng.

Vì vậy, về bản chất, thay vì thực hiện "di chuyển, kiểm tra va chạm, vẽ" bên trong chức năng Paint (), bạn chia "di chuyển" và "vẽ" thành các chức năng riêng biệt mà bạn gọi riêng (trước tiên là "di chuyển" cho mọi đối tượng, sau đó "Vẽ" cho mọi đối tượng). Và giữa những cái đó, kiểm tra va chạm.

Lưu ý nâng cao: Nếu bất kỳ đối tượng nào của bạn tự di chuyển theo phản ứng với các va chạm được phát hiện, thì bạn có thể cần lặp lại bước "tìm va chạm giữa tất cả các cặp đối tượng", trong trường hợp phản ứng va chạm của đối tượng gây ra va chạm khác.


Đây là cách làm đúng đắn. Hãy để các đối tượng xử lý trách nhiệm của họ và hệ thống va chạm sẽ quyết định điều gì xảy ra khi họ gặp một chướng ngại vật. Bạn cũng có thể có một hình chữ nhật va chạm hình trụ (2d / 3d) xung quanh các nhân vật của mình như một loại kích hoạt sớm.
James P.

Tuyệt quá! Về lưu ý nâng cao, các va chạm không nên được kiểm tra lại chỉ đối với các vật thể tự di chuyển khi phản ứng với va chạm và các vật thể chúng va chạm ở vị trí mới? Sẽ có một chuỗi kiểm tra nhưng nó sẽ tránh kiểm tra va chạm cho tất cả các đối tượng.
Cracker


1

Tôi chạy một vòng lặp cho tất cả các nhân vật của tôi trong vòng lặp trò chơi như bạn nói.

Cách tôi làm là với một trạng thái trên mỗi nhân vật của mình, vì vậy nếu A và B va chạm trong khi A đang kiểm tra va chạm thì A và B được thiết lập để đánh. ở đầu vòng lặp B, nó kiểm tra xem nó đã bị tấn công chưa, nếu vậy id không chạy vòng lặp.

Tôi đặt mã ảnh hưởng vào vòng lặp để bất kỳ hành động nào nên thực hiện trên B đã xảy ra trong vòng lặp của A vì vậy không có lý do gì để B kiểm tra vì điều này sẽ làm rối tung kết quả của vụ va chạm, mặc dù điều này có thể khác với bạn .


Nhưng trong trường hợp này khi A phát hiện giao lộ với B, B.hit sẽ được đặt thành đúng và vì vậy B sẽ không kiểm tra giao lộ BẤT K .. Nhưng nếu một nhân vật C khác giao nhau với B, B sẽ không phát hiện ra nó?
Cracker

Xin lỗi, hiểu rồi Vì A không giao nhau với C, C.hit vẫn sẽ sai. B sẽ không kiểm tra va chạm. Nhưng C sẽ kiểm tra và sẽ chuyển thông tin cho B rằng có sự va chạm giữa B và C. Cool!
Cracker

Nhưng tôi đoán nếu tất cả A, B và C giao nhau với nhau sẽ có vấn đề. A sẽ đặt B.hit và C.hit thành đúng. B và C sẽ biết rằng họ đã va chạm với A. Nhưng vì tài sản của họ là đúng nên họ sẽ không kiểm tra va chạm. Sự va chạm giữa B và C sẽ không được chú ý.
Cracker

Bạn có thể lẻn vào một phương thức tương tự bằng cách đặt mọi đối tượng va chạm khả thi vào một bộ sưu tập nào đó, sau đó chỉ kiểm tra va chạm với những thứ xuất hiện sau đối tượng trong bộ sưu tập. IE: A kiểm tra so với B, C, D; B kiểm tra so với C, D; C kiểm tra so với D. Mỗi người phía sau không cần phải kiểm tra vì đã được kiểm tra từ lượt phía sau. Không hoàn toàn nhanh như bỏ qua va chạm hoàn toàn của phần tử, nhưng dù sao cũng hữu ích.
Lunin
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.