How to get the Number of Drawn Triangles reliably in Unreal? - gpu

I am desperately looking for a way to reliably get the average number of triangles drawn during a selected time window in UE 5.1. When I use command line tools for that I get weird numbers. For example, for a scene with a single object that has 220 triangles, RHI Triangles Drawn gives an average of 1607.5 over a 10 second window. I think Unreal includes the number of triangles to render the text it prints on screen (the text on upper left in the image below) which appears when I use command Stat StartFile
I also tried Unreal Insights but I couldn’t find a way to get an average count of triangles drawn over a period from that.
Any ideas to reliably get it?

Related

GODOT: What is an efficient calculation for the AABB of a simple 3D model from a camera's view

I am attempting to come up with a quick and efficient means of translating a 3d mesh into a projected AABB. In the end, I would like to accomplish something similar to figure 1 wherein only the area of the screen covered by the cube is located inside the bounding box highlighted in red. ((if it is at all possible, getting the area as small as possible, highlighted in blue, would increase efficiency down the road.))
Figure 1. https://i.imgur.com/pd0E20C.png
Currently, I have tried:
Calculating the point position on the screen using camera.unproject_position(). this failed largely due to my inability to wrap my head around the pixel positions trending towards infinity. I understand it has something to do with Tan, but frankly, it is too late for my brain to function anymore.
Getting the area of collision between the view frustum and the AABB of the mesh instance. This method seems convoluted, and to get it in a usable format I would need to project the result into 2d coordinates again.
Using the MeshInstance VisualInstance to create a texture wherein a pixel is white if it contains the mesh instance, and black otherwise. Visual instances in general just baffle me, and I did not think it would be efficient to have another viewport just to output this texture.
What I am looking for:
An output that can be passed to a shader informing where to complete certain calculations. Right now this is set up to use a bounding box, but it could easily be rewritten to also use a texture. It also could be rewritten to use polygons, but I am trying to keep calculations to a minimum in the shader.
Certain solutions I have tried before have worked, slightly, but this must be robust. The camera interfacing with the 3d object will be able to move completely around and through it, meaning at times the view will be completely surrounded by the 3d model with points both in front, and behind.
Thank you for any help you can provide.
I will try my best to update this post with information if needed.

Drawing "boxes" on my PDF output

I am working on a corporate-level summary report for my employer. Because this is a fairly high-level report, I'm trying to "pretty" it up a bit (I think the standard SAS output is exceptionally ugly). I've managed to include graphics using ODS REGION and the like, but I'm having trouble generating a fairly basic bar chart.
All I want to do is draw boxes onto the PDF file by specifiying X,Y and W,H and the background color. I've gotten close using this SUGI paper (which employs ODS REGION with a PROC GSLIDE).
That works OK, but I've run into many vexing little issues. For example:
There's a minimum height and width for GSLIDE (appx 3 points) which has made it very difficult to represent small numbers on my bar graph
The corners of GSLIDE are slightly rounded, causing strange looking "artifacts" when attempting to overlay and stack them
There's apparently a "maximum" width (appx 480 points). I think I might be able to solve this with the GOPTIONS VSIZE attribute, but I have to be careful because if the ODS REGION and GSLIDE are exactly the same size, then SAS (for some reason) thinks that the GSLIDE is bigger than the REGION and fails to render GSLIDE properly.
I've searched the internet for an easier approach, but it seems there are few SAS programmers trying to do what I'm doing. I know that I'm reinventing the wheel a bit in that SAS providers bar charts via SAS/GRAPH, but they don't provide the level of customization I need to display the results the way I want them.
How can I draw a simple rectangular shape, with nice square corners, and no weird width/height limitations, on a PDF file?
This isn't direclty relevant to the question, but since it's been brought up, here's an idea of what the bar chart looks like:
Each row measures a metric across a mutually exclusive sub-section of a larger population. The Gray bar represents the total size of the population being measured. The blue bar measures the metric (and the reported number is the metric across the sub-section). The "white bar" is the size of the total population. (The light blue bar is an alternate metric displayed only for those who are curious - it will always be smaller than the blue bar.) Some sub-sections contain no data, so they are displayed as "N/A".
There's also a rolling total. So, after one or a few sub-sections are reported, they are rolled into the rolling total. The gray background groups the related sub-sections, with the rolling total reported at the bottom.
This is pretty much exactly what I want this chart to look like. If it can be done using standard SAS charts, I'd be happy to use them - but I think it's been easier to get this effect on my own by painting the graph myself.
I found a partial answer... you can use a LayoutRegion defined via PROC TEMPLATE to set the background color of an ODS REGION. You still must "put something" within the region to force SAS to render it (for example, ODS TEXT = " ";), but it removes at least one pain point: minimum and maximum sizes.
Unfortunately, the corners are still rounded, but I'll update this answer if I can figure out a way to fix that via an attribute or something.

Rendering a 2D Map in a Game - Cropping and Scrolling

OK.
I'm in essense trying to make my own interpretation of the NES hardware, so I can make a game that ideally would resemble what a NES game would look like. I'm currently stuck with how to adjust how to draw the playfield to the video memory (back buffer).
BACKBUFFER
The NES had restrictions on the nametable, or backbuffer. For my example, the backbuffer is 256x240pixels big, or the size of one screen. If I drew this to the TV, it would fill up the screen perfectly. Now, if I drew this to the screen with an offset of X=5, the entire image would be shifted and would wrap around the screen.
For example.....
ORIGINAL, NO OFFSET: DRAWN WITH OFFSET OF X=5:
ABCDEFGHIJK GHIJKABCDEF
DRAWN WITH OFFSET OF X=-5:
FGHIJKABCDE
The screen is split up into squares 8x8 pixels each, totalling 32x30 rows and columns. (256x240 pixels). The offset is represented in pixels - not columns; so in theory, I could offset the screen by 5 pixels and every column would be shifted to the right by five pixels.
LEVEL DESIGN
My stages are made up of screens, containing data that is represented in 16x15 rows and columns, each by 16x16 pixels. This is to emulate how many NES games stored level data - each tile holds info about what should be in each 8x8 block.
E.g.:
AA
BC with A,B,C,D representing what 8x8 graphic should go where
Level design is represented by this as well, with each number being a different screen and - meaning nothing, null.
-----
-123-
---4-
--54-
-----
CHARACTER PLACEMENT
This is easy. I already know how I can determine which table, row, and column my characters are on based on their absolute positioning. I can also determine the relative positioning within the screen.
With this info, I can easily figure out which columns are to the left and right of the character, if any (if the character is at the left side of screen 1, thered be no more level left)
SO HERE'S THE QUESTION DUN DUN DUN
How do I draw my levels to the screen, so that they scroll from one to the next.
It would be relatively easy to draw one full screen at a time, and when the character gets to the edge just flip to another screen.
However, the problem I'm conceptually having is that I need to 'stream' the level data onto the screen. That, lets say the character moves 24 pixels to the right. The BG needs to move as well.
So, I need to adjust the scrolling of the backbuffer by 24 pixels. However, just scrolling alone will cause the screen to wrap over, diplsaying old portion of the level. So, while scrolling I need to make sure to draw new pieces of the level to the back buffer. But before I can do that, I need to figure out which tiles need to get drawn first. And if the person goes 24 pixels to the left, I need to redraw tiles onto the backbuffer and change the offset accordingly as well.
And let's not forget that if the character moves right and there's no more level data to be drawn, there should be no offset but instead the character gets closer to the side of the screen (instead of being centered in the middle of the screen via the X axis).
Basically, I just have a lot of different numbers and values stuck in my mind right now - trying to wrap my head around many concepts and they caused my brain to turn into goo. Anyone have any perspective on how I can approach this?
EDIT: Using VB.Net. C# is applicable as well ( I program in both)
The way the NES did it was with 4 name tables, each 256x240. When you scrolled one off the screen, the adjacent one would scroll on. To get "worlds" bigger than 512x480, you update the name table at the positions that are offscreen.
Generally, a cartridge would have a giant table in ROM with all of the level data, and would track the overall position with 1 or 2 RAM variables. Then when the game scrolled, it would update the RAM variables, use those to lookup the level data table and copy in the new level data into the parts of the name table that were offscreen.
So actually your back buffer should be 512x480, and you only show a 256x240 portion of it.
Have you looked at the disassembly for any NES games that have large scrolling worlds? I think a partial disassembly of Metroid is out there somewhere...
...yeah, found some docs at romhacking.net
Metroid disassembly; not real well commented but with a little effort it shouldn't be too hard to figure it out.
Another disassembly that is commented better.
EDIT: In the 2nd disassembly posted above, look in MetroidGameEnginePage.txt at the "SetupRoom" routine and the "DrawRoom" routine; also the routine at label LEB4D shows how the name table is updated in one case. Also look at the extensive comments above the "GetNameTable" routine. In general, a text search for "name table" throughout the document will get you lots more.
EDIT EDIT: Also at romhacking.net; the memory map for SMB might be useful.
I would set up a grid of image controls and load the levels from a database that stores what column and row each picture is relative to the level. Once the image that represents the game's character gets far enough to the right (you would have to store its location in some module level variables) of the screen you would load the next column of images (while shifting all of the other images one to the left and removing the first column).

Beat em' up game space management?

I am in the process of making my 2D engine for a Beat'em Up game (Castle Crashers is what I call Beat'em Up or Brawler kind of game ).
I will support 2D sprites and 2D particle emitters. This is all done in the engine now. But I have come to an issue that I would like to ask for advice:
It's about "space" management, what I thought was to do something as this image shows:
alt text http://img337.imageshack.us/img337/9162/spacingprototype1.png
My idea is to make a grid ( Spatial Hash or Grid ), of the ground where my Particle Emitters / 2D sprites will live. In my picture, I have enumerated this slots from 1 to N, (don't have to be 35, it's just for showing purposes ). My idea is to draw the "GameElements" (Sprites/Emitters) in order from 0 to N , ( going from bucket 0 to bucket N ) , so then I will get them to display correctly overlapped on screen (back to forward).
I know this could be done by just comparing the lower Y axis of each Element and performing a "quicksort" too, but having the Grid could allow me to perform Collision Detection in a better way , and if I do something like A* to implement some kind of AI, it could help me too.
If you want to have some sort of optimization for the number of objects you need to test against each other, you might want to think about using a Quadtree
http://en.wikipedia.org/wiki/Quadtree
The idea is to divide the screen up in 4 nodes, placing all items in the node they belong, then divide the nodes you just created up in another 4 if there are sprites/items/whatever in there that need to be tested. Keep doing this until a certain size or amount of items in a node has been reached.
You can then ask the top-node if it contains the item you want to test. This node will then ask the child-nodes if it contains the item, which in their turn will ask their children. This way a large part of the screen can be skipped already (if it's located in child 00, you can skip child 01, 10 and 11). Then you get a list of items you perform more specific collision detection on when it's desired to do so.
If you were to make it visual, it would look a bit like this:
alt text http://geodata.ethz.ch/geovite/tutorials/L2GeodataStructuresAndDataModels/en/images/quadtree.gif
Fire them out to the Z buffer and let that worry about it.
If you find that in the future it is too slow (via profiling obviously) then look at optimizing it.
Take the simplest solution and move on.
Your method fails if you have two sprites occupying the same box in the grid. Suppose you have two enemies both standing in the same box. One stands slightly in front of the other. Which do you draw first? You would need two algorithms - one which divides the sprites into the grid, and the second which looks at the z co-ordinates of all the sprites in a given grid box and draws them based on that value.
A far simpler method is to have a single collection of all sprites. It should store all sprites sorted by their z co-ordinates (from the back of the screen at the head of the list to the front of the screen at the back). Loop through the collection and draw each sprite as it appears. When a sprite moves into or out of the screen (ie. its z co-ordinate changes) you can perform a very simple sort to move that single sprite within the collection. Keep swapping it with the next sprite in the list until the next sprite's z co-ordinate is greater than/less than (as appropriate) the changed sprite's co-ordinate.

Tetravex solving algorithm

Well, i was thinking of making a Tetravex solving program in order to practice my code writing skills (language will propably be Visual Basic) and I need help finding an algorithm for solving it. For those that don't know what tetravex is see this http://en.wikipedia.org/wiki/TetraVex . The only algorithm I can come up with is the brute force way, place a tile randomly in one corner and try every possible tile next to it and continue the same process, if it reaches a dead end revert to a previous state and place a different tile. So can anyone come up with a better algorithm? Thank you for your time.
here some ideas.
A vanilla brute force algorithm would try to fill out the grid recursively by enumerating the grid positions in a fixed order (e.g. row major) and always trying to fit every possible piece in the current position and then recursing. This is what you mentioned and it is very inefficient.
An improvement is to always count for every free position the number of pieces that fit there, and then recurse on the position that has least fits; if one has zero fitting pieces, backtrack immediately; if there is one where only one piece fits fill that and continue (no branch created); otherwise select the one that has least fitting pieces (≥ 2) and continue from there.
Once you have this algorithm in place, the next question is how you can prune the search space more. If have, say, A pieces with "1" on the top position and B pieces with "1" on the bottom position, and A > B, then you know that at least A - B of the "1 at top position" pieces must be actually placed on the top row, so you can exclude them from any other position. This helps to reduce the branching factor and to spot dead-ends earlier.
You should also check at every recursion step that every piece has at least one spot where it fits (do this check after verifying that there is no piece that fits in only one place for speed). If there is a piece that doesn't fit anywhere you need to backtrack immediately. You can extend this to checking that every pair of pieces fits for a potentially better earlier dead-lock checking capability.
There is a also a strategy called "non-chronological backtracking" or "backjumping" which originates from research into SAT solving. This helps you to backtrack more than one level at a time when you reach a dead-end; if you want, you can google for these terms to find more, but you need to do some mental work to map the concept into your problem space.
A first improvement would be counting how many matching pairs of numbers there are, and if, say, there are 5 "1"'s on the top of squares, but only 4 on the bottom, then there must be a "1" pointing off the top of the grid.
At any given partly solved board I would
look for a place where none of the remaining tiles could be played. If found, the board must be unwound to the last place a tile was played randomly.
Look for a place where only 1 of the remaining tiles can legally be played. If found, place that tile.
Place a tile randomly at the spot on the board where the fewest number of remaining tiles can legally be played. Remember this board layout before I lay the tile, I may want to unwind back to this board and play a different tile.
In pseudocode it would be
top:
evaluate # of tiles that match at each empty square
if any square has 0 matches, unwind to <prev>
if any square has 1 match, lay tile, goto top
save current board as <prev>
play randomly at square with minimum number of matches, goto top
As an optimization, you can ignore evaluating squares that don't touch any squares that have tiles, since they will always allow all remaining tiles.
It looks like Tetravex is a Constraint Satisfaction Problem, so you want to limit your options as quickly as possible. It should be possible to do better than random placement. How about?:
Create links between all tile faces with their possible matches.
Any tile with an unlinked face must be an edge tile.
Any tile with two adjacent unlinked faces must be a corner tile.
Center tiles must have four active links.
Now, place a tile in a valid location and invalidate links that are used. If any un-placed tile contains three unlinked faces or unlinked faces on opposite sides, the move is invalid and you can backtrack.
You should be able to use tile face links to look for the next possible tile versus searching through all tiles. If there isn't one, backtrack.
I wrote a solver for Tetravex and used a different approach and it seems very efficient. I built up possible valid relationships increasing the size. So each iteration gives me larger puzzle pieces to work with while reducing the number of puzzle of pieces, so to speak.
I start by creating a list of all possible connections between tiles from bottom to top and a list of all possible connections between tiles from right to left.
From these two lists, I build a list of all possible valid 2x2 combinations.
Using the 2x2 list, I build a list of all possible valid 3x3 combinations.
From there I can go 4x4 by using the 2x2 and 3x3 lists, or do 5x5 by just using the 3x3 list.
Right now my code does each iteration separately, but should be able to be cleaned up to handle each iteration with the same code which would allow for larger grid sizes.
This also seems like a great situation for using a neural net, and I might give that a try next.