Cố gắng sử dụng giấy nến trong 2D trong khi vẫn giữ được độ sâu lớp


7

Đây là màn hình của những gì đang diễn ra để bạn có thể có được một khung tham chiếu.

nhập mô tả hình ảnh ở đây

Vấn đề tôi gặp phải là trò chơi của tôi bị chậm lại do số lượng kết cấu hoán đổi tôi đang thực hiện trong cuộc gọi rút thăm của mình. Vì các bức tường, ký tự, sàn nhà và tất cả các đối tượng nằm trên tấm sprite tương ứng của chúng có chứa các loại đó, mỗi lần vẽ gạch, kết cấu được tải được hoán đổi không dưới 3 đến 5 lần khi nó quay vòng và vẽ các họa tiết để tạo lớp đúng cách.

Bây giờ, tôi đã thử ném tất cả các đối tượng phổ biến vào danh sách tương ứng của chúng, và sau đó sử dụng layerDepth vẽ chúng theo cách đó làm cho mọi thứ tốt hơn rất nhiều, nhưng vấn đề mới mà tôi gặp phải là cách cửa ra vào / cửa sổ của tôi được vẽ trên tường. Cụ thể, tôi đang sử dụng giấy nến để xóa một khối trên các bức tường được vẽ theo hình cửa / cửa sổ để khi bức tường vẽ, nó sẽ có một lỗ có kích thước cửa / cửa sổ trong đó.

Đây là cách mà bản vẽ của tôi được thiết lập cho các bức tường khi tôi đi lát gạch thay vì nhóm các vật thể thông thường.

  1. đầu tiên nó sẽ kiểm tra xem cửa / cửa sổ có ở trên bức tường này không. Nếu không, nó sẽ bỏ qua tất cả các bước và chỉ vẽ bình thường. Nếu không thì
  2. kết thúc spriteBatch hiện tại
  3. Xóa bộ đệm với màu trong suốt để giữ lại những gì đã vẽ
  4. bắt đầu một spritebatch mới với các thiết lập stprint
  5. vẽ khu vực cửa
  6. kết thúc spriteBatch
  7. bắt đầu một spritebatch mới có tính đến stprint đã thiết lập trước đó
  8. vẽ bức tường mà bây giờ sẽ được vẽ với một lỗ trên đó
  9. kết thúc spritebatch
  10. bắt đầu một spritebatch mới với các cài đặt bình thường để tiếp tục vẽ gạch

Trong bản vẽ bằng cách vẽ gạch, việc xóa bộ đệm độ sâu / stpson không thành vấn đề vì tôi không sử dụng bất kỳ lớp nào để sắp xếp những gì vẽ lên trên những gì.

Bây giờ tôi đang vẽ từ danh sách các đối tượng phổ biến thay vì xếp từng ô, nó đã tăng tốc cuộc gọi vẽ của tôi một cách đáng kể nhưng dường như tôi không thể tìm ra cách để giữ cho hệ thống stprint che khuất khu vực cửa ra vào hoặc cửa sổ sẽ được vẽ vào một bức tường. Nguyên nhân của vấn đề là khi tôi kết thúc một spriteBatch để thay đổi DepthStpsonState, nó sẽ làm phẳng RenderTarget hiện tại và không còn bất kỳ sự sắp xếp độ sâu nào cho bất kỳ thứ gì được vẽ sâu hơn nữa. Điều này có nghĩa là các bức tường luôn được vẽ lên trên tất cả mọi thứ, bất kể độ sâu hay vị trí trong thế giới trò chơi và thậm chí là chồng lên nhau vì khuôn tô phải xảy ra một lần cho mỗi bức tường có cửa hoặc cửa sổ.

Có ai biết một cách để có được xung quanh này? Để đun sôi nó xuống, tôi cần một cách để vẽ những thứ được sắp xếp theo độ sâu của lớp trong khi cũng có thể tô khuôn / che đi những phần của các họa tiết cụ thể.


Tôi không biết đủ về XNA để đăng câu trả lời thực sự, nhưng điều này có vẻ đáng ngờ: "khi tôi kết thúc một spriteBatch ... nó sẽ làm phẳng RenderTarget hiện tại và không còn sắp xếp độ sâu nữa". Điều này không nên xảy ra nếu các sprite thực sự bị hút vào bộ đệm sâu (tôi giả sử đó là những gì "layerDepth" làm); thay đổi trạng thái st sâu không cần xóa bộ đệm độ sâu. Vì vậy, có thể đáng để xem xét liệu có cách nào để thay đổi hành vi đó hay không.
Nathan Reed

Khi bạn nói "bắt đầu một spritebatch mới", bạn không có nghĩa là bạn đang tạo một phiên bản SpriteBatch mới, phải không? Tạo một lô mới mỗi khi bạn vẽ một cái gì đó sẽ làm chậm trò chơi của bạn khá nhiều.
Mike Cluck

Câu trả lời:


1

Tôi không biết đủ XNA để cung cấp cho bạn một giải pháp thích hợp, nhưng tôi có thể cho bạn một câu trả lời chung chung.

Vấn đề bạn gặp phải là thuật toán của họa sĩ . Cụ thể, bạn cần phải đặt hàng tất cả những thứ bạn muốn vẽ trước khi bạn có thể vẽ chúng. Cách phổ biến nhất để tránh vấn đề này là với bộ đệm sâu. Thật thú vị, đây còn được gọi là bộ đệm z, vì nó lưu các giá trị z trong không gian máy ảnh.

Tuy nhiên, vì bạn không có Z (vì bạn đang viết trò chơi 2D), bạn không thể sử dụng kỹ thuật này. Hay bạn có thể?

Xem xét điều này: một phép chiếu chính tả không thay đổi phối cảnh của các điểm trong các điểm 3D. Điều này hữu ích cho những thứ như các yếu tố giao diện người dùng, bởi vì bạn luôn muốn chúng giống nhau.

Những gì tôi đề nghị là bạn viết một shader tùy chỉnh lấy ma trận 3D và giá trị độ sâu trên mỗi đỉnh. Giá trị độ sâu này nên được sử dụng để đệm sâu, nhưng không cho chiếu.

Trong giả mã shadercode:

[vertex shader]
pos_output = TransformOrthographic * TransformView * vec3(pos_vertex.x, pos_vertex.y, 0.0);
depth_output = depth_vertex;

[fragment shader]
depth_output = (depth_input - depth_min) / (depth_max - depth_min);

Khi bạn đã thiết lập xong, bạn có thể ngừng lo lắng về việc các đối tượng được hiển thị sai thứ tự và thay vào đó có thể đặt giá trị độ sâu của chúng.

Bây giờ bạn sẽ có thể hiển thị mọi thứ trong một cuộc gọi rút thăm mà không phải lo lắng về việc làm tắt các phần của màn hình.

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.