3d visualisation of real-time data...
i am writing a code to perform 3d visualisation of incoming real-time 8-bit intensity data of a 3d sample (using directx 9 and visual.net)
my code creates 20 slices (along z axis) and using LockRect(), i am creating 20 different textures (i.e. assigning R,G,B,A values based on the given data) and rendering them to those 20 slices. i havent tested my code on real-time data, but i created large amount of 8-bit data representing a sphere (80*80*100) and performed the 3d visualisation using 20 slices. it is working fine with the data i created but am doubtful whether my method is a good one and that will it be able to render real-time data (i.e. data which keeps updating continuosly)?
Yes, it should be possible - but it might require a bit of clever programming. Simply put, locking/modifying resources in Direct3D is slow. Always has been, always will be.
You really need to define a few things:
1. What is "real time" - over the years I've seen definitions varying from 15hz through to 60hz.
2. What sort of hardware are you using? High-end PCI-Express boards with fast CPU's and lost of RAM? or older AGP-based hardware? Does it need to scale, or are you targetting a single configuration?
3. Does it need to be responsive? That is, can you permit a small amount of latency between receiving and displaying the data? Various techniques for efficient/fast resource modification work by using "bounded buffers" (aka ring buffers) and partial/delayed updates, but it can mean that the data shown on screen is a few iterations old...
Give us some more details on those three and we might be able to suggest further advice [smile]
hth
Jack
You really need to define a few things:
1. What is "real time" - over the years I've seen definitions varying from 15hz through to 60hz.
2. What sort of hardware are you using? High-end PCI-Express boards with fast CPU's and lost of RAM? or older AGP-based hardware? Does it need to scale, or are you targetting a single configuration?
3. Does it need to be responsive? That is, can you permit a small amount of latency between receiving and displaying the data? Various techniques for efficient/fast resource modification work by using "bounded buffers" (aka ring buffers) and partial/delayed updates, but it can mean that the data shown on screen is a few iterations old...
Give us some more details on those three and we might be able to suggest further advice [smile]
hth
Jack
Thank You very much for your reply.The following are the replies to your questions:
1. By real-time I mean, data which is changing continuously. For example, the sample could be a frog's heart(the beating of the heart here gives us continuously time-varying data).
2. The hardware we are targetting is High-end PCI-Express boards with lots of RAM.
3. A latency of about 25-100ms (maximum~100ms) is allowed.
I guess thats the information you needed. Please give me some direction for this project.
Thanks in advance,
svpam.
1. By real-time I mean, data which is changing continuously. For example, the sample could be a frog's heart(the beating of the heart here gives us continuously time-varying data).
2. The hardware we are targetting is High-end PCI-Express boards with lots of RAM.
3. A latency of about 25-100ms (maximum~100ms) is allowed.
I guess thats the information you needed. Please give me some direction for this project.
Thanks in advance,
svpam.
As Jack hinted, a carousel-type locking strategy would probably be the best approach for this:
You have a ring of say, 4 dynamic textures in an array. While the card is rendering with one of them, you lock the texture opposite to the active one in the ring, and update it's contents. Come next frame, you rotate the carousel by one step and repeat the process.
This approach minimizes the rendering stall by not having the cpu and gpu try using the same data at the same time. It is impossible to have locks to same resource on both ends of the pipeline - and remember that the gpu holds a lock to the data while rendering it.
You have a ring of say, 4 dynamic textures in an array. While the card is rendering with one of them, you lock the texture opposite to the active one in the ring, and update it's contents. Come next frame, you rotate the carousel by one step and repeat the process.
This approach minimizes the rendering stall by not having the cpu and gpu try using the same data at the same time. It is impossible to have locks to same resource on both ends of the pipeline - and remember that the gpu holds a lock to the data while rendering it.
Hi. I've been working with volume rendering, although not for time-varying data fields. I hope i can give you some pointers :). Some questions to help clarify things:
Are you sure 20 slices will be enough? Some of these volumetric data will go ahead and have resolutions of 128x128x128 and 256x256x256. Maybe the 20 slices will give you a correct view with small resolutions, but it might not scale very well.
As for data (not time varying), you can get some volumes from http://volvis.org/
Also, can the user "browse" arround the data? I mean, change the position and such? I say this because you are taking the slices along the z axis. If the user changes the position/angle it can be a pain. And the transfer functions for color and opacity? Are they constant through the entire application, or can the user change them as well?
There are also some papers about this. There are usually two kind of techniques for volume rendering using graphical hardware: 2D Texture Mapping and 3D Texturing (again, my "personal" perspective from someone who doesnt work with time varying data sets).
For 2D Texture Mapping, the reference paper is usually
"Interactive Volume Rendering on Standard PC Graphics Hardware Using Multi-Textures and Multi-Stage-Rasterization" by Rezk-Salama, Engel, Bauer, Greiner and Ertl.
For 3D Texturing, the initial reference papers are:
"Accelerated volume rendering and tomographic reconstruction using texture mapping hardware"
by Cabral, Cam and Foran
"Direct volume rendering with shading via three-dimensional textures"
by Van Gelder and Kim
"Efficiently using graphics hardware in volume rendering applications"
by Westermann and Ertl
For specific papers, try to google for "time varying volume rendering" or something close to that. Try to focus on papers from acm or ieee.
Hope it helps.
Are you sure 20 slices will be enough? Some of these volumetric data will go ahead and have resolutions of 128x128x128 and 256x256x256. Maybe the 20 slices will give you a correct view with small resolutions, but it might not scale very well.
As for data (not time varying), you can get some volumes from http://volvis.org/
Also, can the user "browse" arround the data? I mean, change the position and such? I say this because you are taking the slices along the z axis. If the user changes the position/angle it can be a pain. And the transfer functions for color and opacity? Are they constant through the entire application, or can the user change them as well?
There are also some papers about this. There are usually two kind of techniques for volume rendering using graphical hardware: 2D Texture Mapping and 3D Texturing (again, my "personal" perspective from someone who doesnt work with time varying data sets).
For 2D Texture Mapping, the reference paper is usually
"Interactive Volume Rendering on Standard PC Graphics Hardware Using Multi-Textures and Multi-Stage-Rasterization" by Rezk-Salama, Engel, Bauer, Greiner and Ertl.
For 3D Texturing, the initial reference papers are:
"Accelerated volume rendering and tomographic reconstruction using texture mapping hardware"
by Cabral, Cam and Foran
"Direct volume rendering with shading via three-dimensional textures"
by Van Gelder and Kim
"Efficiently using graphics hardware in volume rendering applications"
by Westermann and Ertl
For specific papers, try to google for "time varying volume rendering" or something close to that. Try to focus on papers from acm or ieee.
Hope it helps.
Hello Wolverine, I shall answer your questions one by one below:
Right now,I have fixed the number of slices to 20. Eventually, I shall make it a parameter whose value will be decided by the user.
Yes, the user can browse the data with the mouse pointer.But ofcourse, after a certain angle, one would only see the slices and not the entire volume(This is not a prime goal at the present though).
Also Thanks a lot for the info and papers.
Cheers,
svpam.
Right now,I have fixed the number of slices to 20. Eventually, I shall make it a parameter whose value will be decided by the user.
Yes, the user can browse the data with the mouse pointer.But ofcourse, after a certain angle, one would only see the slices and not the entire volume(This is not a prime goal at the present though).
Also Thanks a lot for the info and papers.
Cheers,
svpam.
Also now, I have another problem. My present code has three major functions:
init(),render() and shutdown()
in the init(), i read the sample data into an array and make 20 textures out of it.
in the render(), i render the slices and next shutdown().
now if i have time-varying data,i will have to "re-load" the data array and the 20 textures accordingly. but since the init() is called only once in my code, could you suggest a method whereby i can update and render?
init(),render() and shutdown()
in the init(), i read the sample data into an array and make 20 textures out of it.
in the render(), i render the slices and next shutdown().
now if i have time-varying data,i will have to "re-load" the data array and the 20 textures accordingly. but since the init() is called only once in my code, could you suggest a method whereby i can update and render?
Most multimedia applications tend to run in a loop surrounded by an Initialize() and Terminate() type construct. The main loop is responsible for checking incoming messages (e.g. mouse/keyboard events as well as a new set of data from whatever device you're using) and updating the simulation accordingly. When a certain criteria is met this loop is exited and any existing resources are cleaned up.
To be honest, thats more of a software engineering "puzzle" than a DirectX-specific one. It's largely down to how you want to implement your program and whatever design constraints/requirements you might have.
hth
Jack
InitializeApplication( ); // Create your D3D Device and resources herewhile( ApplicationIsRunning ){ CheckForAnyUserInput( ); // Check for mouse/keyboard events, if the user clicks // "quit" then set ApplicationIsRunning = false CheckForANewDataSample( ); // Update your internal resources to reflect // any newly available data UpdateTheDisplay( ); // (re-)draw the graphics}TerminateApplication( );
To be honest, thats more of a software engineering "puzzle" than a DirectX-specific one. It's largely down to how you want to implement your program and whatever design constraints/requirements you might have.
hth
Jack
Quote:Original post by svpam
Also now, I have another problem. My present code has three major functions:
init(),render() and shutdown()
in the init(), i read the sample data into an array and make 20 textures out of it.
in the render(), i render the slices and next shutdown().
now if i have time-varying data,i will have to "re-load" the data array and the 20 textures accordingly. but since the init() is called only once in my code, could you suggest a method whereby i can update and render?
A straighforward method is to change the render() method to "load" a new time-step volume from time to time in order to achieve animation. The problem with this is the time it takes to load a new volume can drop the frames rates depending of size of the volume.
Done some quick digging in some papers...
What you can also do is use a method called "differential volume rendering". The idea is to pre-process the volumes in order to generate differential files between volume steps. These differential files allow you to discover (with some work) which pixels on the screen change between two consecutive volume time-steps. When you render, you only render the pixels that change.
Also, these guys used compression schemes http://www.vets.ucar.edu/Reports/IEEEVIS01.pdf
for these kinds of rendering. Even if what they've done doesn't suit you, read the previous work section for aditional pointers.
And what you said:
Quote:Original post by svpam
Yes, the user can browse the data with the mouse pointer.But ofcourse, after a certain angle, one would only see the slices and not the entire volume(This is not a prime goal at the present though).
If you are content with not rendering the entire volume from different angles of the viewer, and depending on what exactly is the expected result, some optimizations can be made.
Hi all, right now I am able to update my textures and render them. there is still another problem.
i am creating slices along the z axis. so when i rotate the 3d object i have rendered, say a sphere(for example), after a particular angle what i see is just slices. now if i want to eliminate this problem by making 3 sets of textures along the 3 principal axes and render, how am i to go about it? could u pls elaborate?
i am creating slices along the z axis. so when i rotate the 3d object i have rendered, say a sphere(for example), after a particular angle what i see is just slices. now if i want to eliminate this problem by making 3 sets of textures along the 3 principal axes and render, how am i to go about it? could u pls elaborate?
This topic is closed to new replies.
Advertisement
Popular Topics
Advertisement