<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-8902496644393737364</id><updated>2012-01-28T17:16:40.370Z</updated><category term='detail map'/><category term='rotation'/><category term='nibbles'/><category term='directx'/><category term='texturing'/><category term='fault formation'/><category term='camera'/><category term='software'/><category term='3d'/><category term='blending'/><category term='matrix.rotationyawpitchroll'/><category term='yaw'/><category term='roll'/><category term='engine'/><category term='terrain'/><category term='managed'/><category term='pitch'/><category term='game'/><category term='frustum culling'/><title type='text'>JellyEngine</title><subtitle type='html'>Hi, I'm trying to develop a game in Managed DirectX with procedural textures, procedural cities and eventually full procedural planets but I'm having trouble enough as it is with doing a procedural triangle. Here's where I detail the (slow) development of the (really slow running) game.</subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>38</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-3558387355185111517</id><published>2012-01-28T17:16:00.001Z</published><updated>2012-01-28T17:16:40.395Z</updated><title type='text'>Textured Procedural Planet</title><content type='html'>&lt;p&gt;…aka back to &lt;a href="http://jellyengine.blogspot.com/2008/03/terrain-texturing.html"&gt;square one&lt;/a&gt; albeit the terrain is round this time, so back to round one? I added some textures to the planet, generated on the GPU, they look ok but still lots of work to do. First some outtakes, looked like a load of shite at the start…&lt;/p&gt;  &lt;p align="center"&gt;&lt;a href="http://lh6.ggpht.com/-QGmyadnzUTY/TyQsT1IaBrI/AAAAAAAALt0/M4_VzddaNRc/s1600-h/JellyEngineXna%2525202012-01-27%25252019-15-05-88%25255B19%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; padding-left: 0px; padding-right: 0px; display: inline; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-27 19-15-05-88" border="0" alt="JellyEngineXna 2012-01-27 19-15-05-88" src="http://lh5.ggpht.com/-0CIFfZBDoWU/TyQsUqsSRtI/AAAAAAAALt4/vjg3KY7zzUQ/JellyEngineXna%2525202012-01-27%25252019-15-05-88_thumb%25255B17%25255D.png?imgmax=800" width="235" height="187" /&gt;&lt;/a&gt;&lt;a href="http://lh4.ggpht.com/-0_tfoTZIZEA/TyQsWNo_9TI/AAAAAAAALuE/FC-23aZNNiQ/s1600-h/JellyEngineXna%2525202012-01-27%25252019-15-16-54%25255B19%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; padding-left: 0px; padding-right: 0px; display: inline; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-27 19-15-16-54" border="0" alt="JellyEngineXna 2012-01-27 19-15-16-54" src="http://lh4.ggpht.com/-vqD9nF6063c/TyQsW1a8FAI/AAAAAAAALuI/F1YO3_ItOD8/JellyEngineXna%2525202012-01-27%25252019-15-16-54_thumb%25255B17%25255D.png?imgmax=800" width="235" height="188" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;… then a bit like an old leather ball…&lt;/p&gt;  &lt;p align="center"&gt;&lt;a href="http://lh5.ggpht.com/-_AAV1imAJ2M/TyQsX021KOI/AAAAAAAALuQ/MzIuCApsH8Q/s1600-h/JellyEngineXna%2525202012-01-27%25252019-23-18-91%25255B5%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; padding-left: 0px; padding-right: 0px; display: inline; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-27 19-23-18-91" border="0" alt="JellyEngineXna 2012-01-27 19-23-18-91" src="http://lh6.ggpht.com/-_SbIbYFcIXQ/TyQsYe9w5cI/AAAAAAAALuY/DDDujsV8Oas/JellyEngineXna%2525202012-01-27%25252019-23-18-91_thumb%25255B3%25255D.png?imgmax=800" width="235" height="176" /&gt;&lt;/a&gt;&lt;a href="http://lh3.ggpht.com/-PLelfA54UY8/TyQsZS_t7rI/AAAAAAAALuk/UYOj9HIXhsQ/s1600-h/JellyEngineXna%2525202012-01-27%25252019-26-42-21%25255B4%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; padding-left: 0px; padding-right: 0px; display: inline; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-27 19-26-42-21" border="0" alt="JellyEngineXna 2012-01-27 19-26-42-21" src="http://lh5.ggpht.com/-dR1bfjTNODI/TyQsaORcApI/AAAAAAAALuo/sF7JX_yfTXE/JellyEngineXna%2525202012-01-27%25252019-26-42-21_thumb%25255B2%25255D.png?imgmax=800" width="235" height="176" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;… then all contoury …&lt;/p&gt;  &lt;p align="center"&gt;&lt;a href="http://lh3.ggpht.com/-2UvfAcs5ifY/TyQtBgTIXeI/AAAAAAAALu0/lcHMEdWqKzM/s1600-h/JellyEngineXna%2525202012-01-27%25252019-30-04-16%25255B3%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-27 19-30-04-16" border="0" alt="JellyEngineXna 2012-01-27 19-30-04-16" src="http://lh3.ggpht.com/-4eKs2gYzRXs/TyQtCT9dIBI/AAAAAAAALu8/FGTC7UnfYFM/JellyEngineXna%2525202012-01-27%25252019-30-04-16_thumb%25255B1%25255D.png?imgmax=800" width="235" height="176" /&gt;&lt;/a&gt;&lt;a href="http://lh4.ggpht.com/-m0rb1CvAGG0/TyQtFPePQBI/AAAAAAAALvE/2As-KrDE8N4/s1600-h/JellyEngineXna%2525202012-01-27%25252019-29-49-84%25255B3%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-27 19-29-49-84" border="0" alt="JellyEngineXna 2012-01-27 19-29-49-84" src="http://lh5.ggpht.com/-s25gchSsuH8/TyQtF0MRh_I/AAAAAAAALvM/vVBDLNXfU9M/JellyEngineXna%2525202012-01-27%25252019-29-49-84_thumb%25255B1%25255D.png?imgmax=800" width="235" height="176" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;… (which is actually not too bad looking) then it started to come together a bit …&lt;/p&gt;    &lt;p&gt;&lt;a href="http://lh3.ggpht.com/-VqtZMTew7QY/TyQtJeHJFVI/AAAAAAAALvU/lk6pVBSxLe4/s1600-h/JellyEngineXna%2525202012-01-27%25252019-35-58-32%25255B2%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-27 19-35-58-32" border="0" alt="JellyEngineXna 2012-01-27 19-35-58-32" src="http://lh3.ggpht.com/-QEjVLiHrIyI/TyQtK2-3LsI/AAAAAAAALvc/iX1RCGh9Lec/JellyEngineXna%2525202012-01-27%25252019-35-58-32_thumb.png?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;The problem with this though is that the source texture is applied at the same scale for each patch so there’s a noticeable jump when changing levels, a higher level might show a rock but when it subdivides there are 4 rocks. This gif shows the gifferences when approaching, it looks like the centre patch uses a completely different texture.&lt;/p&gt;  &lt;p align="center"&gt;&lt;a href="http://lh4.ggpht.com/-JSJHHTrbC7E/TyQtMMHzcRI/AAAAAAAALvk/bJcEr4x-VYs/s1600-h/texturemonoscaleprob%25255B2%25255D.gif"&gt;&lt;img style="display: inline" title="texturemonoscaleprob" alt="texturemonoscaleprob" src="http://lh3.ggpht.com/-Migxcsnn2xM/TyQtNsowvcI/AAAAAAAALvs/iV5Zd8cXBx4/texturemonoscaleprob_thumb.gif?imgmax=800" width="240" height="180" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;So it made sense to scale them according to the level (texCoords *= pow(2, maxlevels – patchlevel)), but this introduced some pretty nasty artefacts when zoomed out due to tiling the same texture over and over. Applying mipmapping to the texture I was using helped a bit but it’s still very obvious.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh6.ggpht.com/-l9sfJ8kFnZs/TyQtPfN4FGI/AAAAAAAALv0/a_rukEUHDXs/s1600-h/JellyEngineXna%2525202012-01-28%25252000-26-54-35%25255B2%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-28 00-26-54-35" border="0" alt="JellyEngineXna 2012-01-28 00-26-54-35" src="http://lh3.ggpht.com/-gTY26l4QeTQ/TyQtQf5ZmcI/AAAAAAAALv8/DVhK4ceYoeU/JellyEngineXna%2525202012-01-28%25252000-26-54-35_thumb.png?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;The transitions looked very layered so I added a bit of noise:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh6.ggpht.com/-dOzCefy8b8M/TyQtTGsdDGI/AAAAAAAALwE/4vMCqqx8VoI/s1600-h/JellyEngineXna%2525202012-01-28%25252012-51-12-78%25255B3%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-28 12-51-12-78" border="0" alt="JellyEngineXna 2012-01-28 12-51-12-78" src="http://lh5.ggpht.com/-7gyUjI1sNlk/TyQtUGfQugI/AAAAAAAALwM/AWhTRz0PNRY/JellyEngineXna%2525202012-01-28%25252012-51-12-78_thumb%25255B1%25255D.png?imgmax=800" width="235" height="176" /&gt;&lt;/a&gt;&lt;a href="http://lh4.ggpht.com/-Xp5I34St7MU/TyQtWhgpmjI/AAAAAAAALwU/ivH0Llk892s/s1600-h/JellyEngineXna%2525202012-01-28%25252012-51-43-54%25255B3%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-28 12-51-43-54" border="0" alt="JellyEngineXna 2012-01-28 12-51-43-54" src="http://lh4.ggpht.com/-T-WlQXQ8uz8/TyQtXkDVfHI/AAAAAAAALwc/b8cKrup5La0/JellyEngineXna%2525202012-01-28%25252012-51-43-54_thumb%25255B1%25255D.png?imgmax=800" width="235" height="176" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;All in all it’s not bad for a first go but could be a lot better. I was having fun flying about the place so I made a little video:&lt;/p&gt;  &lt;div style="padding-bottom: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; float: none; padding-top: 0px" id="scid:5737277B-5D6D-4f48-ABFC-DD9C333F4C5D:62b58d4f-8d3f-457c-ae60-76ef980b6b9c" class="wlWriterEditableSmartContent"&gt;&lt;div id="f50dcffd-3422-4f66-940a-787be40e4b54" style="margin: 0px; padding: 0px; display: inline;"&gt;&lt;div&gt;&lt;a href="http://www.youtube.com/watch?v=fqbYW6_h5Zw" target="_new"&gt;&lt;img src="http://lh3.ggpht.com/-VPpqwyIBfkc/TyQtYMuejWI/AAAAAAAALwg/UqyOn0HqOsI/video792f58956da3%25255B79%25255D.jpg?imgmax=800" style="border-style: none" galleryimg="no" onload="var downlevelDiv = document.getElementById('f50dcffd-3422-4f66-940a-787be40e4b54'); downlevelDiv.innerHTML = &amp;quot;&amp;lt;div&amp;gt;&amp;lt;object width=\&amp;quot;448\&amp;quot; height=\&amp;quot;252\&amp;quot;&amp;gt;&amp;lt;param name=\&amp;quot;movie\&amp;quot; value=\&amp;quot;http://www.youtube.com/v/fqbYW6_h5Zw?hl=en&amp;amp;hd=1\&amp;quot;&amp;gt;&amp;lt;\/param&amp;gt;&amp;lt;embed src=\&amp;quot;http://www.youtube.com/v/fqbYW6_h5Zw?hl=en&amp;amp;hd=1\&amp;quot; type=\&amp;quot;application/x-shockwave-flash\&amp;quot; width=\&amp;quot;448\&amp;quot; height=\&amp;quot;252\&amp;quot;&amp;gt;&amp;lt;\/embed&amp;gt;&amp;lt;\/object&amp;gt;&amp;lt;\/div&amp;gt;&amp;quot;;" alt=""&gt;&lt;/a&gt;&lt;/div&gt;&lt;/div&gt;&lt;/div&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;p&gt;…then noticed a problem I had neglected from before that’s obvious in lines going through the brown pit on the right at 0:34.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh6.ggpht.com/-g8FeBHK0Rys/TyQtaKrdWmI/AAAAAAAALws/3Is0w4TUD2s/s1600-h/JellyEngineXna%2525202012-01-28%25252012-19-10-78%25255B2%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-28 12-19-10-78" border="0" alt="JellyEngineXna 2012-01-28 12-19-10-78" src="http://lh6.ggpht.com/-nQ7xHHBCGrg/TyQtbducoqI/AAAAAAAALw0/TvUeUs4qv8Q/JellyEngineXna%2525202012-01-28%25252012-19-10-78_thumb.png?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;I thought it was cracking at first because it only seemed to occur when creating other patches but investigating it further it wasn’t cracking, but something to do with textures. Another gif to show the gifferences…&lt;/p&gt;  &lt;p align="center"&gt;&lt;a href="http://lh4.ggpht.com/-VYLEQOrlY5M/TyQtcSgi3bI/AAAAAAAALw8/OTmDDbpKQKc/s1600-h/pointlinearclampproblem%25255B2%25255D.gif"&gt;&lt;img style="display: inline" title="pointlinearclampproblem" alt="pointlinearclampproblem" src="http://lh3.ggpht.com/-5uNFuo3FaYM/TyQtdcix75I/AAAAAAAALxE/mxLybPdBTro/pointlinearclampproblem_thumb.gif?imgmax=800" width="240" height="180" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;The points are fine, it’s the texture on top that’s creating the artefact. What it ended up being was a leftover setting from creating patches. In order to get the heights from the GPU I draw the noise for each vertex in a patch to an image and read them back to reset the vertices. In order for neighbouring patches to have the same height values &lt;a href="http://jellyengine.blogspot.com/2011/06/gpu-planet-update.html"&gt;I draw it as a point-clamped list of lines&lt;/a&gt;. When this was happening a subsequent draw would use the point-clamped sampler and create the artefact. Looking for how to fix led to some &lt;a href="http://blogs.msdn.com/b/shawnhar/archive/2010/04/02/state-objects-in-xna-game-studio-4-0.aspx"&gt;good advice&lt;/a&gt;, don’t assume sampler states when drawing, explicitly set them every time you need them.&lt;/p&gt;  &lt;p&gt;I’ve found &lt;a href="http://johnwhigham.blogspot.com/"&gt;a&lt;/a&gt; few &lt;a href="http://evasion.inrialpes.fr/~Eric.Bruneton/"&gt;other&lt;/a&gt; very &lt;a href="http://procworld.blogspot.com/"&gt;impressive&lt;/a&gt; procedural &lt;a href="http://www.gamedev.net/blog/1302/entry-2250847-bow-shock-a-summary-of-work-done-so-far"&gt;planet&lt;/a&gt; projects so I might trawl their blogs to see if they mention how to do textures so well. So for next time…&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;Adding noise to the texture isn’t great, needs a good bit of tweaking. I could try to do a look-up table &amp;amp; incorporate slope as in &lt;a href="http://www.gamedev.net/blog/73/entry-1692117-terrain-texturing-explained/"&gt;this old post from Ysaneya (Infinity)&lt;/a&gt;.&lt;/li&gt;    &lt;li&gt;I need to hide tiling somehow, it occurs and is dealt with in the old post from Ysaneya above but the description is just “lighting, shadowing, other effects”.&lt;/li&gt;    &lt;li&gt;I’ll need a better noise algo, the one I’m using is very homogenous (“samey”). This project called &lt;a href="http://lithosphere.codeflow.org/"&gt;lithosphere&lt;/a&gt; might help find a good one quickly.&lt;/li&gt;    &lt;li&gt;The FPS are struggling whenever creating patches &amp;amp; I’m not showing that many polys so I might need to do some optimisation. I pass data around a lot between CPU and GPU so I think these &lt;a href="http://blogs.msdn.com/b/shawnhar/archive/2008/03/31/an-elf-in-a-box.aspx"&gt;articles&lt;/a&gt; by Shawn Hargreaves might help find out if I’m &lt;a href="http://blogs.msdn.com/b/shawnhar/archive/2008/04/07/how-to-tell-if-you-are-cpu-or-gpu-bound.aspx"&gt;CPU or GPU bound&lt;/a&gt; and try to balance both.&lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;Lots to do!&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-3558387355185111517?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/3558387355185111517/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=3558387355185111517' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/3558387355185111517'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/3558387355185111517'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2012/01/textured-procedural-planet.html' title='Textured Procedural Planet'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh5.ggpht.com/-0CIFfZBDoWU/TyQsUqsSRtI/AAAAAAAALt4/vjg3KY7zzUQ/s72-c/JellyEngineXna%2525202012-01-27%25252019-15-05-88_thumb%25255B17%25255D.png?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-1197132118077844235</id><published>2012-01-17T23:43:00.001Z</published><updated>2012-01-17T23:43:28.854Z</updated><title type='text'>Less Abnormal…</title><content type='html'>&lt;p&gt;This problem took me MONTHS to resolve. First I had to laze about and ignore it for about 6 months until a new year’s resolution made me look at it again. The problem is that each patch is created independently (i.e. it might not have any neighbours yet), so when calculating the normal vectors at the edges the normal calculation is biased towards itself. It’s kinda hard to explain in words so hopefully a diagram will help:&lt;/p&gt;  &lt;p align="center"&gt;&lt;a href="http://lh4.ggpht.com/-nTCqTdyZwJ4/TxYHX2n6kqI/AAAAAAAALsQ/o2kXUo3zafk/s1600-h/image%25255B10%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="image" border="0" alt="image" src="http://lh3.ggpht.com/-xZkl-jpRiMs/TxYHYd9f4cI/AAAAAAAALsU/YCw-GRoTzdI/image_thumb%25255B4%25255D.png?imgmax=800" width="389" height="165" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;A normal is a normalised vector perpendicular to the surface at a certain point, it might help if you imagine walking on the surface, at peaks and troughs you’ll be upright but on slopes you’ll have to compensate by leaning in (or fall over whatever floats your boat). In this example, I’m trying to work out what the normals are for the green “patch” (the green V) and I don’t yet have the blue or the red patch. So I have to calculate a normal (pink arrows) for each of the 3 points in the green patch using just those 3 points.&lt;/p&gt;  &lt;p&gt;I can work out the centre normal fully using the 2 adjacent points to the left and the right. However the left and right normals only have 2 points available (left &amp;amp; centre for the left normal, right &amp;amp; centre for the right normal) for normal calculation and so they end up perpendicular to the left and right vectors. When the red patch comes along it happens to work out well, the normal on the right indicates a slope. Unfortunately when the blue patch comes along it&amp;#160; will look wrong. The left normal should be pointing straight up because it’s a peak, not a slope. If that wasn’t enough, to make matters worse when the blue patch works out its right normal it will look like a slope in the opposite direction so lighting will shade the slopes with a very sharp divide at the top.&lt;/p&gt;  &lt;p&gt;In order to solve I could redo neighbouring normals whenever a new patch is generated but this would cause lots of rewriting the vertex buffer &amp;amp; would be visually obvious until the neighbouring patch was created. The way I opted for was to extend the patch area by one cell (equivalent to getting the middle point of the blue and red patches) and work out normals for all the inner points (same number of points as in the unextended patch). It worked out pretty well, here’s a before and after shot where latitude lines disappear:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh5.ggpht.com/--ih_Wtr_aVA/TxYHaje4OJI/AAAAAAAALsg/ev2S2BsjGWI/s1600-h/JellyEngineXna%2525202012-01-17%25252021-35-20-06%25255B2%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-17 21-35-20-06" border="0" alt="JellyEngineXna 2012-01-17 21-35-20-06" src="http://lh4.ggpht.com/-Y-aZfHeGHTk/TxYHcPzVveI/AAAAAAAALso/4wjQ8Zu6c6c/JellyEngineXna%2525202012-01-17%25252021-35-20-06_thumb.png?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh6.ggpht.com/-rIkxiXNdjPU/TxYHeWGeJUI/AAAAAAAALsw/1igMsi7o5k0/s1600-h/JellyEngineXna%2525202012-01-17%25252021-35-25-64%25255B2%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-17 21-35-25-64" border="0" alt="JellyEngineXna 2012-01-17 21-35-25-64" src="http://lh3.ggpht.com/-AfsGZ8EzLLM/TxYHfQ4r-pI/AAAAAAAALs4/aUmt08Y3z1w/JellyEngineXna%2525202012-01-17%25252021-35-25-64_thumb.png?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;And a close up with pink normals. On the peak in the before shot there’s divergence with normals at the same point going different directions. In the after shot the normals on the peak look like one normal but really they are 4 different normals all pointing in the same direction:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/-bdrz0N3b7eI/TxYHhMidWtI/AAAAAAAALtA/Htt7cne3iYI/s1600-h/JellyEngineXna%2525202012-01-17%25252021-40-58-54%25255B2%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-17 21-40-58-54" border="0" alt="JellyEngineXna 2012-01-17 21-40-58-54" src="http://lh5.ggpht.com/-nTYeKMZ_K2I/TxYHiSWtyOI/AAAAAAAALtI/X519F3_xrj0/JellyEngineXna%2525202012-01-17%25252021-40-58-54_thumb.png?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh3.ggpht.com/-fn3-LxdT9Sg/TxYHj1GNhbI/AAAAAAAALtQ/Rak4wMzBvb4/s1600-h/JellyEngineXna%2525202012-01-17%25252021-41-10-70%25255B2%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2012-01-17 21-41-10-70" border="0" alt="JellyEngineXna 2012-01-17 21-41-10-70" src="http://lh3.ggpht.com/-gDYquGxgEGI/TxYHlOoI7LI/AAAAAAAALtY/PfKDJQ5t_pE/JellyEngineXna%2525202012-01-17%25252021-41-10-70_thumb.png?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;It’s a bit less obvious but on the mountain side you can see some lines caused by divergent normals where patches meet in the before shot disappear in the after. I made a gif to show gifferences but the 256 colour palette isn’t the best:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh3.ggpht.com/-DmYHF2agGwo/TxYHmNyQj9I/AAAAAAAALtg/4waFWrRLTMs/s1600-h/peak%25255B3%25255D.gif"&gt;&lt;img style="display: inline" title="peak" alt="peak" src="http://lh5.ggpht.com/-VBdX2fgpObI/TxYHngMUbqI/AAAAAAAALto/Zy6lazA5m9g/peak_thumb%25255B1%25255D.gif?imgmax=800" width="480" height="364" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;I think I’ll have a little look at texturing next, to get the planet looking like the terrain I had SEVERAL years ago… pretty shameful thinking this is progressing so slow but sure I’ll keep tapping away at it, one day at a time*.&lt;/p&gt;  &lt;p&gt;*time may be anything from 6 months to a year or two!&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-1197132118077844235?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/1197132118077844235/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=1197132118077844235' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/1197132118077844235'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/1197132118077844235'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2012/01/less-abnormal.html' title='Less Abnormal…'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh3.ggpht.com/-xZkl-jpRiMs/TxYHYd9f4cI/AAAAAAAALsU/YCw-GRoTzdI/s72-c/image_thumb%25255B4%25255D.png?imgmax=800' height='72' width='72'/><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-3504368610682171222</id><published>2011-07-31T23:40:00.001+01:00</published><updated>2011-07-31T23:45:55.827+01:00</updated><title type='text'>Added (ab)Normals</title><content type='html'>&lt;p&gt;I had a go at adding normals to all the vertices on the planet and it had a pretty dramatic effect. I started off with an algorithm from … &lt;a href="http://www.gamedev.net/topic/163625-fast-way-to-calculate-heightmap-normals/"&gt;here&lt;/a&gt; … site seems to be down at the moment though. Anyways, I converted it to work with triangle strips and got some pretty nice results:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh6.ggpht.com/--R_BzlYA_Mk/TjXZ5be_agI/AAAAAAAALrI/oO5saouXt3g/s1600-h/JellyEngineXna%2525202011-07-25%25252022-35-12-36%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2011-07-25 22-35-12-36" border="0" alt="JellyEngineXna 2011-07-25 22-35-12-36" src="http://lh6.ggpht.com/-PvXj5sVT7Bw/TjXZ6P3o_lI/AAAAAAAALrM/Iqf-DG-ZpaQ/JellyEngineXna%2525202011-07-25%25252022-35-12-36_thumb.jpg?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;I threw in another planet in the background to look like a moon, textures are still non-existent.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh3.ggpht.com/-VShaaS8QfnQ/TjXZ6lYfUFI/AAAAAAAALrQ/dX0M60b_9ow/s1600-h/JellyEngineXna%2525202011-07-28%25252016-12-12-09%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2011-07-28 16-12-12-09" border="0" alt="JellyEngineXna 2011-07-28 16-12-12-09" src="http://lh3.ggpht.com/-Ro2QgTQ_UcI/TjXZ7LrBBVI/AAAAAAAALrU/F5tDIlo8sfI/JellyEngineXna%2525202011-07-28%25252016-12-12-09_thumb.jpg?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;There are some problems with this technique though, namely that the vertices at the edges (and especially the corners) of patches calculate their normal from a smaller number of connections – so there’s always seams between patches, and exaggerated peaks at corners… looks a bit like the labels are coming off…&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/-tPx_Ga9S4mk/TjXZ76anK6I/AAAAAAAALrY/ektWtPaAjY0/s1600-h/JellyEngineXna%2525202011-07-26%25252010-39-41-82%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2011-07-26 10-39-41-82" border="0" alt="JellyEngineXna 2011-07-26 10-39-41-82" src="http://lh4.ggpht.com/-F5sPc-kcvqg/TjXZ8LXWV0I/AAAAAAAALrc/O-Vd3srBs5M/JellyEngineXna%2525202011-07-26%25252010-39-41-82_thumb.jpg?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;I *think* the solution is to either share the edges between patches (but that might force me to do SetData on 4 neighbouring patches – very slow), or for each patch to generate more data than it will show, e.g. a 1-cell skirt around the existing patch.&lt;/p&gt;  &lt;p&gt;There’s also some weird effect going on around ridges, maybe because the diagonals are longer so should be weighted differently? I’m hoping it’ll go away when I use a normal map… after I figure out how to generate it first! :)&lt;/p&gt;  &lt;p&gt;Other than that I put normals on the trees (much easier) and implemented a recycling scheme so patches that weren’t used wouldn’t keep a hold on memory. One result of all the above work is that there are cracks in the patches again so I’ll have to revisit my LOD decision stuff… one step forward, two steps back, then get hit by a bus.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-3504368610682171222?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/3504368610682171222/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=3504368610682171222' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/3504368610682171222'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/3504368610682171222'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2011/07/added-abnormals.html' title='Added (ab)Normals'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh6.ggpht.com/-PvXj5sVT7Bw/TjXZ6P3o_lI/AAAAAAAALrM/Iqf-DG-ZpaQ/s72-c/JellyEngineXna%2525202011-07-25%25252022-35-12-36_thumb.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-9145109128498789139</id><published>2011-07-24T16:54:00.001+01:00</published><updated>2011-07-24T16:54:47.454+01:00</updated><title type='text'>L-System Trees</title><content type='html'>&lt;p&gt;I continued working with the &lt;a href="http://algorithmicbotany.org/papers/#otherdocs"&gt;Algorithmic Beauty of Plants&lt;/a&gt; book and implemented parametric and context-sensitivity from chapter 1, made the trees from 3D tubes (instead of lines) and tried some of the examples from chapter 2 &lt;a href="http://algorithmicbotany.org/papers/abop/abop-ch2.pdf"&gt;Modeling of trees&lt;/a&gt;. I had some success but couldn’t reproduce some of the models, mainly the section with tri-branching trees.&lt;/p&gt;  &lt;p&gt;Here’s my results of the rules on page 56 varied with the parameters on page 57:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh5.ggpht.com/-DRpl2BaUU08/TixAFUt_j1I/AAAAAAAALpY/awk3LUHDDTs/s1600-h/p56%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="p56" border="0" alt="p56" src="http://lh6.ggpht.com/-_gbuTZuWLiE/TixAF1EO-7I/AAAAAAAALpc/6caCYa44TTc/p56_thumb.jpg?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;And here’s what the original ones from the book look like:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh6.ggpht.com/-hJuL1MxDDms/TixAGtCXCoI/AAAAAAAALpg/CpJVT51jUK0/s1600-h/p56original%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="p56original" border="0" alt="p56original" src="http://lh6.ggpht.com/-Vs8WVFD-wAo/TixAG1QaN6I/AAAAAAAALpk/D3frG4RFq_Q/p56original_thumb.jpg?imgmax=800" width="284" height="349" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;They look pretty similar, apart from (b). Note that in (b) the height of my version is the same as the other trees, but in the book it is much shorter. This is odd because the table on page 57 modifies the branch contraction rate (&lt;em&gt;r&lt;sub&gt;2&lt;/sub&gt;&lt;/em&gt;) only, not the trunk contraction rate (&lt;em&gt;r&lt;sub&gt;2&lt;/sub&gt;&lt;/em&gt;) which is always 0.9 so they should all be the same height.&lt;/p&gt;  &lt;p&gt;In fact, it’s not clear what the height should be to get the above images as the axiom at the start sets the length to 1 and the width to 10, and if the length:width ratio really were 1:10, the result would be a lot more squat, like this:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/-unWtVh6rV6w/TixAHKHDX6I/AAAAAAAALpo/4hhh7dUBuHQ/s1600-h/JellyEngineXna%2525202011-07-24%25252015-10-02-33%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2011-07-24 15-10-02-33" border="0" alt="JellyEngineXna 2011-07-24 15-10-02-33" src="http://lh4.ggpht.com/-41ILJ7c7b30/TixAHsX5vEI/AAAAAAAALps/tY-F64RfnDk/JellyEngineXna%2525202011-07-24%25252015-10-02-33_thumb.jpg?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;And it’s still pretty squat at 10:10:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh3.ggpht.com/-hMsm85onEkM/TixAH3svabI/AAAAAAAALpw/8FuhKGeKeow/s1600-h/JellyEngineXna%2525202011-07-24%25252015-10-26-57%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2011-07-24 15-10-26-57" border="0" alt="JellyEngineXna 2011-07-24 15-10-26-57" src="http://lh5.ggpht.com/-UZtgGkrqJgU/TixAIc2HmRI/AAAAAAAALp0/aiXqkRGiais/JellyEngineXna%2525202011-07-24%25252015-10-26-57_thumb.jpg?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;I found a ratio of 100:10 worked best to yield results similar to the book.&lt;/p&gt;  &lt;p&gt;The experiments on page 59 looked pretty much identical to the book (again using a ratio of 100:10 so an initial axiom of A(100,10) instead of A(1,10)), here’s mine:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh3.ggpht.com/-_XYe9lxnAvo/TixAI2A_l9I/AAAAAAAALp4/s6j0ZbM7i9Y/s1600-h/p59%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="p59" border="0" alt="p59" src="http://lh3.ggpht.com/-j9h35KQ2p3c/TixAJP-O41I/AAAAAAAALp8/m-yZfA8H0Gk/p59_thumb.jpg?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;And here’s the books:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh5.ggpht.com/-vT1OD4G4iV8/TixAJlZ20BI/AAAAAAAALqA/0OiOdhA3T3A/s1600-h/p59original%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="p59original" border="0" alt="p59original" src="http://lh6.ggpht.com/-Mhq3kqYs4RQ/TixAKO7Vx3I/AAAAAAAALqE/jNPLp4sH01c/p59original_thumb.jpg?imgmax=800" width="331" height="349" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;I had the least luck with reproducing the examples under Ternary branching. In the book (a) is shown as:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh3.ggpht.com/-3_QxCokYins/TixAKc4NzcI/AAAAAAAALqI/lbGuoS00yKI/s1600-h/image%25255B2%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="image" border="0" alt="image" src="http://lh6.ggpht.com/-D6vS8GxGOSI/TixAK0CyXWI/AAAAAAAALqM/YycLCPCsa1Y/image_thumb.png?imgmax=800" width="371" height="349" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;… which has a degree of irregularity… I don’t know where the model can get this as there is no stochasticity specified and the tropism applied is straight down (like the force of gravity), so why would the branch on the right bow down more than any other branch? My results show a much more regular model:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/-4kiPybEu4q8/TixALazet3I/AAAAAAAALqQ/i-DuJMi6LYA/s1600-h/p60a%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="p60a" border="0" alt="p60a" src="http://lh4.ggpht.com/-6IwL8VbLeyg/TixAL29E3NI/AAAAAAAALqU/Jek613SN4_g/p60a_thumb.jpg?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;The closest of the ternary branching section I got was (b), although I had to fiddle with a few parameters (setting the width increase rate to 1.432 instead of the 1.732 given). Here’s the version in the book:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/-jF3mzYZrnCQ/TixAMAazysI/AAAAAAAALqY/nbnp6CAJoQM/s1600-h/image%25255B5%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="image" border="0" alt="image" src="http://lh6.ggpht.com/-Zlg8vAWahdg/TixAM74qWII/AAAAAAAALqc/u05gzL8losQ/image_thumb%25255B1%25255D.png?imgmax=800" width="377" height="349" /&gt;&lt;/a&gt;&lt;/p&gt;                  &lt;p&gt;And here’s my result:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh6.ggpht.com/-Ec-zK8EvwRQ/TixANv9HHfI/AAAAAAAALqg/6qxDMqeJeJk/s1600-h/p60b%252520vr1.432%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="p60b vr1.432" border="0" alt="p60b vr1.432" src="http://lh6.ggpht.com/-4DTTWpZab3g/TixAOBFtCxI/AAAAAAAALqk/PkS4ClzFHOs/p60b%252520vr1.432_thumb.jpg?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;(c) and (d) were real headaches… I can’t get these to look anything like the ones in the book… I’m pretty sure something’s missing ar the parameters specified are wrong, especially the elongation rate (&lt;em&gt;l&lt;sub&gt;r&lt;/sub&gt;&lt;/em&gt;) for (c); on page 61 it’s defined as 1.790 and all the others are 1.1 or less. Plugging this into my L-System/turtle interpreter results in a very tall tree (looking up at it in the first image and looking head on but zoomed out enough to see whole tree in the second):&lt;/p&gt;    &lt;p&gt;&lt;a href="http://lh6.ggpht.com/-GSM64zd8puc/TixAOYuYZnI/AAAAAAAALqo/NGS_il2E77E/s1600-h/JellyEngineXna%2525202011-07-24%25252015-38-40-99%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2011-07-24 15-38-40-99" border="0" alt="JellyEngineXna 2011-07-24 15-38-40-99" src="http://lh4.ggpht.com/-yZVQgCX2YmM/TixAO7f0szI/AAAAAAAALqs/Czx2Z6BFQtw/JellyEngineXna%2525202011-07-24%25252015-38-40-99_thumb.jpg?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh6.ggpht.com/-YpkKmL2Z_uw/TixAPPMZxnI/AAAAAAAALqw/CTD39tTXK9k/s1600-h/JellyEngineXna%2525202011-07-24%25252015-39-01-39%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2011-07-24 15-39-01-39" border="0" alt="JellyEngineXna 2011-07-24 15-39-01-39" src="http://lh5.ggpht.com/-W8jYdh_YPEg/TixAPVj_esI/AAAAAAAALq0/Wl-c6H0ezpE/JellyEngineXna%2525202011-07-24%25252015-39-01-39_thumb.jpg?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;I’m pretty sure my coding is right on this one, if you take the start piece from the axiom which is defined as F(200) and apply &lt;em&gt;p2&lt;/em&gt; (F(l) –&amp;gt; F(l*l&lt;sub&gt;r&lt;/sub&gt;) 8 times with l&lt;sub&gt;r&lt;/sub&gt; set to 1.790, this is the same as 200*(1.790&lt;sup&gt;8&lt;/sup&gt;) which is about &lt;a href="http://www.google.co.uk/search?aq=f&amp;amp;sourceid=chrome&amp;amp;ie=UTF-8&amp;amp;q=200*(1.790^8)"&gt;21079&lt;/a&gt;. For the other trees, l&lt;sub&gt;r&lt;/sub&gt; is 1.109 and the base trunk height after 8 iterations of &lt;em&gt;p2&lt;/em&gt; would be 200*(1.109&lt;sup&gt;8&lt;/sup&gt;) which is about &lt;a href="http://www.google.co.uk/search?sourceid=chrome&amp;amp;ie=UTF-8&amp;amp;q=200*(1.109^8)"&gt;457&lt;/a&gt;. However the image in the book shows the tree as the same height and roughly the same proportion to its width as the other examples:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/-d2Bd01flQAk/TixAP_XIeFI/AAAAAAAALq4/A2mKaHo1_jA/s1600-h/image%25255B8%25255D.png"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="image" border="0" alt="image" src="http://lh5.ggpht.com/-7nw03uhPbJ0/TixAQqqCqMI/AAAAAAAALq8/JRCZt7tPuRw/image_thumb%25255B2%25255D.png?imgmax=800" width="344" height="349" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;If I muck about with the parameters a bit I can get something that looks a bit more like it:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh6.ggpht.com/-3ym5Xrl3G_8/TixARY3sxlI/AAAAAAAALrA/3nBoeQdkWhc/s1600-h/JellyEngineXna%2525202011-07-24%25252015-47-56-31%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-bottom: 0px; border-left: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top: 0px; border-right: 0px; padding-top: 0px" title="JellyEngineXna 2011-07-24 15-47-56-31" border="0" alt="JellyEngineXna 2011-07-24 15-47-56-31" src="http://lh5.ggpht.com/-OxvQotMWn9w/TixARliiskI/AAAAAAAALrE/pAXJUjn98is/JellyEngineXna%2525202011-07-24%25252015-47-56-31_thumb.jpg?imgmax=800" width="438" height="328" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;… but it’s not quite as nice. (d) is the same story really, can’t reproduce it from the parameters given… :(&lt;/p&gt;  &lt;p&gt;I’m *pretty* sure I’m right but this book has been out since 1990 and there’s nothing specified in the &lt;a href="http://algorithmicbotany.org/papers/abop/abop_errata.html"&gt;errata&lt;/a&gt;. I tried to find these models in the &lt;a href="http://algorithmicbotany.org/virtual_laboratory/"&gt;virtual lab&lt;/a&gt; available from &lt;a href="http://algorithmicbotany.org/"&gt;algorithmicbotany.org&lt;/a&gt; but no luck. So I might fire off an email and see if any one associated with the book can help me out…&lt;/p&gt;  &lt;p&gt;Other than that I implemented horizon culling on the planet with a lot of help from an article at &lt;a href="http://www.crappycoding.com/2009/04/horizon-culling-3-finale/"&gt;crappy coding&lt;/a&gt;, redid some of my basic rotation stuff (I had everything mirrored through the z axis), and tried to streamline how new patches are formed on the planet (it didn’t work!). I’m not sure what to do next, had a look at some demoscene programs and am now utterly depressed at how little I’ve done! I might try generating normal maps from the heightmap of a planet patch for lighting, maybe do atmospheric scattering, texturing of the planet and/or trees, adding leaves maybe? Hiring someone else to do this for me?? :)&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-9145109128498789139?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/9145109128498789139/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=9145109128498789139' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/9145109128498789139'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/9145109128498789139'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2011/07/l-system-trees.html' title='L-System Trees'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh6.ggpht.com/-_gbuTZuWLiE/TixAF1EO-7I/AAAAAAAALpc/6caCYa44TTc/s72-c/p56_thumb.jpg?imgmax=800' height='72' width='72'/><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-1545531557683741976</id><published>2011-06-14T12:18:00.001+01:00</published><updated>2011-06-14T12:53:12.697+01:00</updated><title type='text'>GPU Planet Update</title><content type='html'>&lt;p&gt;Jeez, I can’t believe it’s been almost 2 years since I last did anything with this… I picked it up again a few weeks ago and tried to get into it again, made a little progress and thought I’d share.&lt;/p&gt;  &lt;p&gt;A major problem getting back into it was migrating from XNA 3.1 to XNA 4 – there are lots and lots of changes, one of the worst I found was the restrictions placed on shaders and the Reach and HiDef profiles. I found an article which described &lt;a href="http://communistgames.blogspot.com/2010/11/targeting-reach-and-hidef-pcs-with-same.html"&gt;how to target Reach and HiDef with the same project&lt;/a&gt; which was very handy, otherwise I’d have to develop 2 separate projects in parallel if I wanted to use both of my laptops for developing (one’s far more portable than the other but has to be Reach). So with a lot of help from &lt;a href="http://www.nelxon.com/blog/xna-3-1-to-xna-4-0-cheatsheet/"&gt;this cheat sheet&lt;/a&gt; I got my project running again, and tried to learn a bit about shaders to see if I could get GPU noise back on shaders less than version 3_0_0.&lt;/p&gt;  &lt;p&gt;In the process, I used a ping-pong technique to create Conway’s Game Of Life simulation (much better in 1080p):&lt;/p&gt;  &lt;div style="padding-bottom: 0px; margin: 0px auto; padding-left: 0px; width: 448px; padding-right: 0px; display: block; float: none; padding-top: 0px" id="scid:5737277B-5D6D-4f48-ABFC-DD9C333F4C5D:d50c2651-a394-4171-8974-c42f6aa87f1f" class="wlWriterEditableSmartContent"&gt;&lt;div id="8efa9de1-aa4a-4a0a-ad02-94ffbba40410" style="margin: 0px; padding: 0px; display: inline;"&gt;&lt;div&gt;&lt;a href="http://www.youtube.com/watch?v=_5K0fBuJ46w" target="_new"&gt;&lt;img src="http://lh3.ggpht.com/-tl-pHj2sR6E/TfdLpJQvnfI/AAAAAAAALpI/xWj-fgE-h-M/video0d3243d8d979%25255B3%25255D.jpg?imgmax=800" style="border-style: none" galleryimg="no" onload="var downlevelDiv = document.getElementById('8efa9de1-aa4a-4a0a-ad02-94ffbba40410'); downlevelDiv.innerHTML = &amp;quot;&amp;lt;div&amp;gt;&amp;lt;object width=\&amp;quot;448\&amp;quot; height=\&amp;quot;252\&amp;quot;&amp;gt;&amp;lt;param name=\&amp;quot;movie\&amp;quot; value=\&amp;quot;http://www.youtube.com/v/_5K0fBuJ46w?hl=en&amp;amp;hd=1\&amp;quot;&amp;gt;&amp;lt;\/param&amp;gt;&amp;lt;embed src=\&amp;quot;http://www.youtube.com/v/_5K0fBuJ46w?hl=en&amp;amp;hd=1\&amp;quot; type=\&amp;quot;application/x-shockwave-flash\&amp;quot; width=\&amp;quot;448\&amp;quot; height=\&amp;quot;252\&amp;quot;&amp;gt;&amp;lt;\/embed&amp;gt;&amp;lt;\/object&amp;gt;&amp;lt;\/div&amp;gt;&amp;quot;;" alt=""&gt;&lt;/a&gt;&lt;/div&gt;&lt;/div&gt;&lt;/div&gt;  &lt;p&gt;The next stage then was to get back to the original goal of getting the GPU to generate all the noise as &lt;a href="http://jellyengine.blogspot.com/2009/12/procedural-lod-planet-textures.html"&gt;I found out&lt;/a&gt; doing noise in software was far too slow.&lt;/p&gt;  &lt;p&gt;The plan was to pass the vertices to the shaders, let them calculate the noise then get back a heightmap which I can use to update the vertices. One of the problems was that the vertices form a curved surface and I need to flatten it for the pixel shader to give me back a regular heightmap. As each of my patches has texture coordinates that go from 0,0 to 1,1 I can create a flat image that the pixel shader could work with by using the texture coordinate to generate the position in clip space and storing the original position –which the shader will use to get the noise- in a texture coordinate. So for example, a point at 123, 234, 345 with texture coordinate 0.5,0.5 would end up in clip space at position 0,0 (clip space goes from –1 to 1) with the position stored as a texture coordinate. There’s &lt;a href="http://drilian.com/2008/11/25/understanding-half-pixel-and-half-texel-offsets/"&gt;a problem with halfpixel offsets as Drilian describes&lt;/a&gt;, in the end my shaders look something like this:&lt;/p&gt;  &lt;pre class="csharpcode"&gt;&lt;span class="kwrd"&gt;struct&lt;/span&gt; vertexInput {&lt;br /&gt;    float4 position        : POSITION;&lt;br /&gt;    float2 texcoord        : TEXCOORD;&lt;br /&gt;};&lt;br /&gt; &lt;br /&gt;&lt;span class="kwrd"&gt;struct&lt;/span&gt; vertexOutput {&lt;br /&gt;   float4 hPosition        : POSITION;&lt;br /&gt;   float3 wPosition        : TEXCOORD1;&lt;br /&gt;};&lt;br /&gt; &lt;br /&gt;&lt;span class="kwrd"&gt;float&lt;/span&gt; texel;&lt;br /&gt;vertexOutput VS_flat(vertexInput IN) &lt;br /&gt;{&lt;br /&gt;    vertexOutput OUT;&lt;br /&gt;    &lt;span class="kwrd"&gt;float&lt;/span&gt; clipx = 2 * IN.texcoord.x - 1;&lt;br /&gt;    &lt;span class="kwrd"&gt;float&lt;/span&gt; clipy = 2 * -IN.texcoord.y + 1;&lt;br /&gt;    float4 clipPosition = float4(clipx - texel, clipy + texel, 0, 1);&lt;br /&gt;    OUT.hPosition = clipPosition;&lt;br /&gt; &lt;br /&gt;    OUT.wPosition = IN.position.xyz;&lt;br /&gt; &lt;br /&gt;    &lt;span class="kwrd"&gt;return&lt;/span&gt; OUT;&lt;br /&gt;}&lt;br /&gt;    &lt;br /&gt;float4 PS_noise(vertexOutput IN): COLOR&lt;br /&gt;{&lt;br /&gt;    float3 p = 0;&lt;br /&gt;    p = IN.wPosition;&lt;br /&gt;    &lt;span class="kwrd"&gt;return&lt;/span&gt; inoise(p)*0.5+0.5;&lt;br /&gt;}&lt;/pre&gt;&lt;br /&gt;&lt;style type="text/css"&gt;&lt;br /&gt;.csharpcode, .csharpcode pre&lt;br /&gt;{&lt;br /&gt;	font-size: small;&lt;br /&gt;	color: black;&lt;br /&gt;	font-family: consolas, "Courier New", courier, monospace;&lt;br /&gt;	background-color: #ffffff;&lt;br /&gt;	/*white-space: pre;*/&lt;br /&gt;}&lt;br /&gt;.csharpcode pre { margin: 0em; }&lt;br /&gt;.csharpcode .rem { color: #008000; }&lt;br /&gt;.csharpcode .kwrd { color: #0000ff; }&lt;br /&gt;.csharpcode .str { color: #006080; }&lt;br /&gt;.csharpcode .op { color: #0000c0; }&lt;br /&gt;.csharpcode .preproc { color: #cc6633; }&lt;br /&gt;.csharpcode .asp { background-color: #ffff00; }&lt;br /&gt;.csharpcode .html { color: #800000; }&lt;br /&gt;.csharpcode .attr { color: #ff0000; }&lt;br /&gt;.csharpcode .alt &lt;br /&gt;{&lt;br /&gt;	background-color: #f4f4f4;&lt;br /&gt;	width: 100%;&lt;br /&gt;	margin: 0em;&lt;br /&gt;}&lt;br /&gt;.csharpcode .lnum { color: #606060; }&lt;/style&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;And this technique let me create fBm on a 2_0_0 pixel shader by adding each stage of fBm in separate ping-pong passes:&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;div style="padding-bottom: 0px; margin: 0px auto; padding-left: 0px; width: 448px; padding-right: 0px; display: block; float: none; padding-top: 0px" id="scid:5737277B-5D6D-4f48-ABFC-DD9C333F4C5D:5ea075bd-32f3-4a1c-9b08-ebd31ceb016b" class="wlWriterEditableSmartContent"&gt;&lt;div id="ede15061-2b4a-4ee0-a33b-9b8d7d572166" style="margin: 0px; padding: 0px; display: inline;"&gt;&lt;div&gt;&lt;a href="http://www.youtube.com/watch?v=GLIJHaTg2mI" target="_new"&gt;&lt;img src="http://lh3.ggpht.com/-QNixkNIFpVU/TfdKe4W4LrI/AAAAAAAALpM/fKZw6RAOXcI/videoc0c665eabe2c%25255B3%25255D.jpg?imgmax=800" style="border-style: none" galleryimg="no" onload="var downlevelDiv = document.getElementById('ede15061-2b4a-4ee0-a33b-9b8d7d572166'); downlevelDiv.innerHTML = &amp;quot;&amp;lt;div&amp;gt;&amp;lt;object width=\&amp;quot;448\&amp;quot; height=\&amp;quot;252\&amp;quot;&amp;gt;&amp;lt;param name=\&amp;quot;movie\&amp;quot; value=\&amp;quot;http://www.youtube.com/v/GLIJHaTg2mI?hl=en&amp;amp;hd=1\&amp;quot;&amp;gt;&amp;lt;\/param&amp;gt;&amp;lt;embed src=\&amp;quot;http://www.youtube.com/v/GLIJHaTg2mI?hl=en&amp;amp;hd=1\&amp;quot; type=\&amp;quot;application/x-shockwave-flash\&amp;quot; width=\&amp;quot;448\&amp;quot; height=\&amp;quot;252\&amp;quot;&amp;gt;&amp;lt;\/embed&amp;gt;&amp;lt;\/object&amp;gt;&amp;lt;\/div&amp;gt;&amp;quot;;" alt=""&gt;&lt;/a&gt;&lt;/div&gt;&lt;/div&gt;&lt;/div&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;I used this in my original project and tried to update the vertices given the heightmap values generated by the shader. This didn’t work initially, I ended up with lots of cracks because of the way the pixel shader interpolates.&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;a href="http://lh4.ggpht.com/-eXjiFHDJdqo/TfdKgqpWqjI/AAAAAAAALoo/BSovVg6XOmI/s1600-h/JellyEngineXna%2525202011-06-11%25252020-31-45-30.png"&gt;&lt;img style="background-image: none; border-right-width: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px; padding-top: 0px" title="JellyEngineXna 2011-06-11 20-31-45-30" border="0" alt="JellyEngineXna 2011-06-11 20-31-45-30" src="http://lh5.ggpht.com/-75CcE_NpZtM/TfdKieHIEzI/AAAAAAAALos/MB1GtIPQvGE/JellyEngineXna%2525202011-06-11%25252020-31-45-30_thumb.png?imgmax=800" width="438" height="342" /&gt;&lt;/a&gt;&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;The upper left point (at tex coord 0,0) would have the correct noise value but I couldn’t get the lower right point to draw the correct noise value at tex coord 1,1. When 2 patches met they would have different height values for the same vertex. In the end I managed to get around it by rendering using a line-strip instead of a triangle-strip. This picture shows the same noise values along the edges of the patches:&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;a href="http://lh6.ggpht.com/-42LmeIakreY/TfdKi723L-I/AAAAAAAALow/PvLplWTqD14/s1600-h/JellyEngineXna%2525202011-06-14%25252010-47-12-57%25255B2%25255D.jpg"&gt;&lt;img style="background-image: none; border-right-width: 0px; margin: 0px auto; padding-left: 0px; padding-right: 0px; display: block; float: none; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px; padding-top: 0px" title="JellyEngineXna 2011-06-14 10-47-12-57" border="0" alt="JellyEngineXna 2011-06-14 10-47-12-57" src="http://lh3.ggpht.com/-xTiBCQBxoqc/TfdKjS9CpiI/AAAAAAAALo0/rnYzg0oy9Xs/JellyEngineXna%2525202011-06-14%25252010-47-12-57_thumb.jpg?imgmax=800" width="438" height="342" /&gt;&lt;/a&gt;&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;So, although it looks like I’ve made almost no progress since about 3 years ago (yikes!), I have! … made almost no progress that is :) The main difference is that this planet can render at run time – all the other planets had to have some pre-rendering of some sort, here’s a little fly around at 17x17 vertices per patch so you can see popping and subdividing:&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;div style="padding-bottom: 0px; margin: 0px auto; padding-left: 0px; width: 448px; padding-right: 0px; display: block; float: none; padding-top: 0px" id="scid:5737277B-5D6D-4f48-ABFC-DD9C333F4C5D:ac8774da-ee39-456e-8f08-0d050314e6f8" class="wlWriterEditableSmartContent"&gt;&lt;div id="a863913a-9d43-4dc6-a309-02bd4d06efcd" style="margin: 0px; padding: 0px; display: inline;"&gt;&lt;div&gt;&lt;a href="http://www.youtube.com/watch?v=HXP5eviZiX8" target="_new"&gt;&lt;img src="http://lh5.ggpht.com/-O12LOAHFF_o/TfdKj4rm67I/AAAAAAAALpQ/Ep2MXIZolmk/videodfda3a477409%25255B3%25255D.jpg?imgmax=800" style="border-style: none" galleryimg="no" onload="var downlevelDiv = document.getElementById('a863913a-9d43-4dc6-a309-02bd4d06efcd'); downlevelDiv.innerHTML = &amp;quot;&amp;lt;div&amp;gt;&amp;lt;object width=\&amp;quot;448\&amp;quot; height=\&amp;quot;252\&amp;quot;&amp;gt;&amp;lt;param name=\&amp;quot;movie\&amp;quot; value=\&amp;quot;http://www.youtube.com/v/HXP5eviZiX8?hl=en&amp;amp;hd=1\&amp;quot;&amp;gt;&amp;lt;\/param&amp;gt;&amp;lt;embed src=\&amp;quot;http://www.youtube.com/v/HXP5eviZiX8?hl=en&amp;amp;hd=1\&amp;quot; type=\&amp;quot;application/x-shockwave-flash\&amp;quot; width=\&amp;quot;448\&amp;quot; height=\&amp;quot;252\&amp;quot;&amp;gt;&amp;lt;\/embed&amp;gt;&amp;lt;\/object&amp;gt;&amp;lt;\/div&amp;gt;&amp;quot;;" alt=""&gt;&lt;/a&gt;&lt;/div&gt;&lt;/div&gt;&lt;/div&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;In the end… it might be better to generate all the noise every time, for the vertices and for the pixels, caching the vertex info and texture is very heavy on memory. Hmm what’ll I work on next for an update in 2013…&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-1545531557683741976?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/1545531557683741976/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=1545531557683741976' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/1545531557683741976'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/1545531557683741976'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2011/06/gpu-planet-update.html' title='GPU Planet Update'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh3.ggpht.com/-tl-pHj2sR6E/TfdLpJQvnfI/AAAAAAAALpI/xWj-fgE-h-M/s72-c/video0d3243d8d979%25255B3%25255D.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-5080662165670060960</id><published>2009-12-24T20:15:00.001Z</published><updated>2009-12-24T20:15:56.036Z</updated><title type='text'>Blooming Starfields</title><content type='html'>&lt;p&gt;It took AGES to add bloom. I used an &lt;a href="http://creators.xna.com/en-US/sample/bloom"&gt;XNA tutorial&lt;/a&gt; for bloom and in order to do the various passes (pick the brightest spots, blur it, recombine with the original image) it called ResolveBackBuffer to copy the back buffer to a texture for the next pass. I don’t fully understand it yet but it seems this call would invalidate the back buffer and subsequent shaders would write as if they were the first. I’ll try to illustrate what I mean by showing the problems I had. My plan was to draw the stars &amp;amp; clusters first, bloom that, then add the nebula.&lt;/p&gt;  &lt;p&gt;Here’s what the result was like without the bloom stage, the nebula is added to the background stars (no bloom) as expected:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/_GaS6iHPgjYA/SzPL4R9XYXI/AAAAAAAALe4/XExX15NLCbU/s1600-h/starfield%20without%20bloom%5B4%5D.jpg"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="starfield without bloom" border="0" alt="starfield without bloom" src="http://lh3.ggpht.com/_GaS6iHPgjYA/SzPL5NWDfBI/AAAAAAAALe8/6YfZrGwv7vk/starfield%20without%20bloom_thumb%5B2%5D.jpg?imgmax=800" width="500" height="377" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;And here with the bloom stage included in the middle, it seems to be overwritten by the nebula stage:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh5.ggpht.com/_GaS6iHPgjYA/SzPL54FusHI/AAAAAAAALfA/dK_k1jQf0oM/s1600-h/nebula%20overwrites%20starfield%20with%20bloom%5B3%5D.jpg"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="nebula overwrites starfield with bloom" border="0" alt="nebula overwrites starfield with bloom" src="http://lh5.ggpht.com/_GaS6iHPgjYA/SzPL6ZWsadI/AAAAAAAALfE/gfsgKgFjc1Y/nebula%20overwrites%20starfield%20with%20bloom_thumb%5B1%5D.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; In the end, I did a ResolveBackBuffer to a ResoveTarget2D after the bloom stage and drew this to the back buffer before I call the fBm/nebula shader. This finally ended in what I was looking for.&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh5.ggpht.com/_GaS6iHPgjYA/SzPL9EVJ9FI/AAAAAAAALfI/SkrLtxdbgv0/s1600-h/starfield%20with%20bloom%5B3%5D.jpg"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="starfield with bloom" border="0" alt="starfield with bloom" src="http://lh6.ggpht.com/_GaS6iHPgjYA/SzPL9-rP4wI/AAAAAAAALfM/z38lBWmwIjo/starfield%20with%20bloom_thumb%5B1%5D.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;I’m still not 100% happy with the results, I had imagined the bloomed background stars would really light up the nebula but they seem to actually be dimmer than the stars outside of the nebula. I might try to use the same fBm noise result to draw some stars so they are in place in the densest parts of the nebula.&lt;/p&gt;  &lt;p&gt;The main thing I’m not happy with though is that the code is a total mess, I just kept hacking and hacking away until I got results. I’m sure a team of monkeys would have produced neater code in less time. It’ll be a while before I get these images into a skybox – so until then HAPPY CHRISTMAS!&lt;/p&gt;  &lt;div style="padding-bottom: 0px; margin: 0px auto; padding-left: 0px; width: 425px; padding-right: 0px; display: block; float: none; padding-top: 0px" id="scid:5737277B-5D6D-4f48-ABFC-DD9C333F4C5D:18b550fa-8746-4349-8bc2-6bfbcebc85cb" class="wlWriterEditableSmartContent"&gt;&lt;div id="76ab09c7-b489-4acb-bec5-023d965c26b6" style="margin: 0px; padding: 0px; display: inline;"&gt;&lt;div&gt;&lt;a href="http://www.youtube.com/watch?v=Ev9lt1iazL8" target="_new"&gt;&lt;img src="http://lh4.ggpht.com/_GaS6iHPgjYA/SzPL-jkO8_I/AAAAAAAALfQ/cO_4PpD_I-U/videodb53e92c78e9%5B3%5D.jpg?imgmax=800" style="border-style: none" galleryimg="no" onload="var downlevelDiv = document.getElementById('76ab09c7-b489-4acb-bec5-023d965c26b6'); downlevelDiv.innerHTML = &amp;quot;&amp;lt;div&amp;gt;&amp;lt;object width=\&amp;quot;425\&amp;quot; height=\&amp;quot;355\&amp;quot;&amp;gt;&amp;lt;param name=\&amp;quot;movie\&amp;quot; value=\&amp;quot;http://www.youtube.com/v/Ev9lt1iazL8&amp;amp;hl=en\&amp;quot;&amp;gt;&amp;lt;\/param&amp;gt;&amp;lt;embed src=\&amp;quot;http://www.youtube.com/v/Ev9lt1iazL8&amp;amp;hl=en\&amp;quot; type=\&amp;quot;application/x-shockwave-flash\&amp;quot; width=\&amp;quot;425\&amp;quot; height=\&amp;quot;355\&amp;quot;&amp;gt;&amp;lt;\/embed&amp;gt;&amp;lt;\/object&amp;gt;&amp;lt;\/div&amp;gt;&amp;quot;;" alt=""&gt;&lt;/a&gt;&lt;/div&gt;&lt;/div&gt;&lt;/div&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-5080662165670060960?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/5080662165670060960/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=5080662165670060960' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/5080662165670060960'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/5080662165670060960'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2009/12/blooming-starfields.html' title='Blooming Starfields'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh3.ggpht.com/_GaS6iHPgjYA/SzPL5NWDfBI/AAAAAAAALe8/6YfZrGwv7vk/s72-c/starfield%20without%20bloom_thumb%5B2%5D.jpg?imgmax=800' height='72' width='72'/><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-8029624506042350608</id><published>2009-12-24T00:00:00.001Z</published><updated>2009-12-24T00:00:02.020Z</updated><title type='text'>Procedural Starfield Texture (First Go)</title><content type='html'>&lt;p&gt;I decided to try my hand at a procedural starfield. I figured it’d be an easy enough shader to do (I’m still a total beginner) plus I’ll need to use the same techniques to generate cached images of planet patches (previous GPU noise posts were generated per-pixel every frame). So I started off with some blue fractal Brownian motion noise for the background:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/_GaS6iHPgjYA/SzKu4AtxM1I/AAAAAAAALeQ/xuDVxEKCQgs/s1600-h/stars_fBm%5B3%5D.jpg"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="stars_fBm" border="0" alt="stars_fBm" src="http://lh3.ggpht.com/_GaS6iHPgjYA/SzKu5CvMvFI/AAAAAAAALeU/J9H23Sg9kqs/stars_fBm_thumb%5B1%5D.jpg?imgmax=800" width="375" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;And added some code to make simple noise white if it were over a certain threshold. I thought these would appear as stars, but it was all blobby:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh3.ggpht.com/_GaS6iHPgjYA/SzKu5kkmV5I/AAAAAAAALeY/iYCWUJcgtoA/s1600-h/stars_fBmn%5B2%5D.jpg"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="stars_fBmn" border="0" alt="stars_fBmn" src="http://lh6.ggpht.com/_GaS6iHPgjYA/SzKu6PBX7BI/AAAAAAAALec/pYYIiYz3nI8/stars_fBmn_thumb.jpg?imgmax=800" width="375" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;So then I scaled it by passing p*scale instead of p to inoise:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/_GaS6iHPgjYA/SzKu8IftzOI/AAAAAAAALeg/L9Tv74jGrAs/s1600-h/stars_fBmsn%5B2%5D.jpg"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="stars_fBmsn" border="0" alt="stars_fBmsn" src="http://lh3.ggpht.com/_GaS6iHPgjYA/SzKu9FgItoI/AAAAAAAALek/p3KizwwZSfg/stars_fBmsn_thumb.jpg?imgmax=800" width="375" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;Not bad… but the stars (little blobs) are too generic so I added in another layer of noise but at a second scale (bigger blobs) so it looks like brighter stars or clustering:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh5.ggpht.com/_GaS6iHPgjYA/SzKu9oDEAGI/AAAAAAAALeo/W9Ih_J_fOt4/s1600-h/stars_fBmsnc%5B2%5D.jpg"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="stars_fBmsnc" border="0" alt="stars_fBmsnc" src="http://lh4.ggpht.com/_GaS6iHPgjYA/SzKu-dSE6VI/AAAAAAAALes/kyO7Oq-RjE4/stars_fBmsnc_thumb.jpg?imgmax=800" width="375" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;It looks ok… a bit lame though… The problems I see are that the stars have aliasing artefacts and the scene doesn’t … impress. Zoomed in the stars look crap, like Tetris blocks or something:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh3.ggpht.com/_GaS6iHPgjYA/SzKu-rzWGlI/AAAAAAAALew/nY3E0NgFwFE/s1600-h/stars%20aliased%20unimpressive%5B6%5D.jpg"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="stars aliased unimpressive" border="0" alt="stars aliased unimpressive" src="http://lh5.ggpht.com/_GaS6iHPgjYA/SzKu_H2a3BI/AAAAAAAALe0/VlLPAfUMgvg/stars%20aliased%20unimpressive_thumb%5B2%5D.jpg?imgmax=800" width="164" height="162" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;I think it needs some effects like glow or bloom or &lt;a href="http://www.vgcats.com/comics/?strip_id=224"&gt;MORE BLOOM&lt;/a&gt;! So I’ll look into that next.&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;Here’s the shader code so far, pretty simple stuff:&lt;/p&gt;  &lt;p&gt;vertexOutput VS(vertexInput IN)    &lt;br /&gt;{    &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160; vertexOutput OUT;    &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160; OUT.hPosition = IN.position;    &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160; OUT.texcoord&amp;#160; = IN.texcoord * noiseScale;    &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160; OUT.wPosition = IN.position.xyz * noiseScale;    &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160; return OUT;    &lt;br /&gt;} &lt;/p&gt;  &lt;p&gt;float4 PS_test(vertexOutput IN): COLOR   &lt;br /&gt;{    &lt;br /&gt;&amp;#160; float3 p = IN.wPosition;    &lt;br /&gt;&amp;#160; float res = fBm(p, oct, lac, gain);    &lt;br /&gt;&amp;#160; float4 color = res;    &lt;br /&gt;&amp;#160; color.rg = 0; // make it blue    &lt;br /&gt;&amp;#160; color.a = 1;    &lt;br /&gt;&amp;#160; float star = inoise(p * speckleScale);    &lt;br /&gt;&amp;#160; if (star &amp;gt; speckle)    &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160; color = lerp(color, star, 0.9); &lt;/p&gt;  &lt;p&gt;&amp;#160; float starcluster = inoise(p * speckleScale2);   &lt;br /&gt;&amp;#160; if (starcluster &amp;gt; speckle2 + 0.1)    &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160; color = lerp(color, starcluster, 0.9);    &lt;br /&gt;&amp;#160; return color;    &lt;br /&gt;} &lt;/p&gt;  &lt;p&gt;technique test   &lt;br /&gt;{    &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160; pass p0    &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160; {    &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160; VertexShader = compile vs_3_0 VS();    &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160; PixelShader&amp;#160; = compile ps_3_0 PS_test();    &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160; }    &lt;br /&gt;}&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-8029624506042350608?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/8029624506042350608/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=8029624506042350608' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/8029624506042350608'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/8029624506042350608'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2009/12/procedural-starfield-texture-first-go.html' title='Procedural Starfield Texture (First Go)'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh3.ggpht.com/_GaS6iHPgjYA/SzKu5CvMvFI/AAAAAAAALeU/J9H23Sg9kqs/s72-c/stars_fBm_thumb%5B1%5D.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-6523658624898108946</id><published>2009-12-21T15:31:00.001Z</published><updated>2009-12-21T16:18:11.619Z</updated><title type='text'>GPU Perlin Noise</title><content type='html'>&lt;p&gt;I updated my DirectX before starting and somehow my MDX project became all liney, like this:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh6.ggpht.com/_GaS6iHPgjYA/Sy-UvkNoReI/AAAAAAAALdM/LO3RQMIgMyA/s1600-h/Uhhh2.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="Uhhh" border="0" alt="Uhhh" src="http://lh6.ggpht.com/_GaS6iHPgjYA/Sy-Uwn3Yh3I/AAAAAAAALdQ/y8EvtX3b3vM/Uhhh_thumb.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;Because of this, and because most of the online samples I find to &lt;strike&gt;plagiarize&lt;/strike&gt; be inspired by are usually in XNA I decided to convert. Unfortunately there’s no automatic conversion tool so I had to open a new project, add my old files and try to fix up the errors. Some things were annoying, like the lack of absolute mouse movement and having to load a font from a file (size is fixed in the file) but overall the classes are better named and organised. Here’s my first shader on the planet in XNA, stripes:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/_GaS6iHPgjYA/Sy-UxMUMsdI/AAAAAAAALdU/XENMW5G-fvE/s1600-h/stripey2.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="stripey" border="0" alt="stripey" src="http://lh5.ggpht.com/_GaS6iHPgjYA/Sy-U0TmQjGI/AAAAAAAALdY/aaq23BDs8kg/stripey_thumb.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;So after a quick crash course on shaders, I found Perlin had &lt;a href="http://http.developer.nvidia.com/GPUGems2/gpugems2_chapter26.html"&gt;published HLSL code&lt;/a&gt; for Improved Perlin noise in &lt;a href="http://developer.nvidia.com/object/gpu_gems_2_home.html"&gt;GPU Gems 2&lt;/a&gt; – all of which is free online! I had real trouble getting it going however, every texture I generated was blank, and I didn’t know enough about HLSL to figure it out. There seemed to be a tutorial on ziggyware but it seems ziggyware’s been under attack from hackers so I couldn’t get it. I tried out some other projects like &lt;a href="http://drilian.com/2007/10/17/procedual-terseness/"&gt;Drilian’s&lt;/a&gt; but again the XNA version I made the noise didn’t work. Eventually I found a &lt;a href="http://forums.xna.com/forums/p/10684/56446.aspx"&gt;post where someone&lt;/a&gt; had similar problems, which led me to the &lt;a href="http://209.85.229.132/search?q=cache:pT1xY3lxnWYJ:www.ziggyware.com/weblinks.php%3Fcat_id%3D9%26weblink_id%3D5232+xna+inoise&amp;amp;cd=2&amp;amp;hl=en&amp;amp;ct=clnk&amp;amp;gl=ie"&gt;Google cache of the XNA GPU Perlin noise tutorial&lt;/a&gt; – by Patrick of &lt;a href="http://recreationstudios.blogspot.com/"&gt;recreationstudios&lt;/a&gt; (he’s made some amazing progress since I deserted this project 2 years ago). All I needed to do was initialise the textures all the noise functions use. Perlin had functions to do this in HLSL, but I hadn’t a clue how to call them, supposedly you can’t in XNA so I moved the HLSL code to C# then create the textures on the CPU and set the textures on the GPU. Patrick’s tutorial explains this much better (prize-winningly better apparently) so I won’t go into details.&lt;/p&gt;  &lt;p&gt;So here are some screens of different types of Perlin noise on the planet:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh6.ggpht.com/_GaS6iHPgjYA/Sy-U1KYGsDI/AAAAAAAALdc/W8aO5QB_uPs/s1600-h/Noise2.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="Noise" border="0" alt="Noise" src="http://lh4.ggpht.com/_GaS6iHPgjYA/Sy-U1p2S_4I/AAAAAAAALdg/GqbccFWCEsU/Noise_thumb.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/_GaS6iHPgjYA/Sy-U2LUIVEI/AAAAAAAALdk/PscKBzfhirA/s1600-h/NoiseRidgedMF2.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="NoiseRidgedMF" border="0" alt="NoiseRidgedMF" src="http://lh5.ggpht.com/_GaS6iHPgjYA/Sy-U2zvOQSI/AAAAAAAALdo/yijd9WHS6k8/NoiseRidgedMF_thumb.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;In these shots the noise is being calculated per-pixel each frame based on the geometry. Surprisingly, getting closer to the planet so the level of detail is higher (the 4 child patches are drawn instead of the parent patch) didn’t change the surface visibly. This had to do with the fact that there wasn’t much geometry difference between the parents and the children, when I changed the patch size from 33x33 to 5x5 there was definite popping in the textures.&lt;/p&gt;  &lt;p&gt;Here’s a video of flying about a bit:&lt;/p&gt;  &lt;div style="padding-bottom: 0px; margin: 0px auto; padding-left: 0px; width: 425px; padding-right: 0px; display: block; float: none; padding-top: 0px" id="scid:5737277B-5D6D-4f48-ABFC-DD9C333F4C5D:dc76b5aa-1292-47f4-af04-e7bf46c7f5d4" class="wlWriterEditableSmartContent"&gt;&lt;div id="06dced21-421a-4593-8546-8f4a74a66844" style="margin: 0px; padding: 0px; display: inline;"&gt;&lt;div&gt;&lt;a href="http://www.youtube.com/watch?v=a-cr8K1tVvQ" target="_new"&gt;&lt;img src="http://lh6.ggpht.com/_GaS6iHPgjYA/Sy-U4oFYzII/AAAAAAAALd8/cpqjskldn94/video175cbe991154%5B9%5D.jpg?imgmax=800" style="border-style: none" galleryimg="no" onload="var downlevelDiv = document.getElementById('06dced21-421a-4593-8546-8f4a74a66844'); downlevelDiv.innerHTML = &amp;quot;&amp;lt;div&amp;gt;&amp;lt;object width=\&amp;quot;425\&amp;quot; height=\&amp;quot;355\&amp;quot;&amp;gt;&amp;lt;param name=\&amp;quot;movie\&amp;quot; value=\&amp;quot;http://www.youtube.com/v/a-cr8K1tVvQ&amp;amp;hl=en\&amp;quot;&amp;gt;&amp;lt;\/param&amp;gt;&amp;lt;embed src=\&amp;quot;http://www.youtube.com/v/a-cr8K1tVvQ&amp;amp;hl=en\&amp;quot; type=\&amp;quot;application/x-shockwave-flash\&amp;quot; width=\&amp;quot;425\&amp;quot; height=\&amp;quot;355\&amp;quot;&amp;gt;&amp;lt;\/embed&amp;gt;&amp;lt;\/object&amp;gt;&amp;lt;\/div&amp;gt;&amp;quot;;" alt=""&gt;&lt;/a&gt;&lt;/div&gt;&lt;/div&gt;&lt;/div&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;&lt;font color="#ff0000"&gt;Update&lt;/font&gt;: shading every frame means I can animate!&lt;/p&gt;  &lt;div style="padding-bottom: 0px; margin: 0px auto; padding-left: 0px; width: 425px; padding-right: 0px; display: block; float: none; padding-top: 0px" id="scid:5737277B-5D6D-4f48-ABFC-DD9C333F4C5D:4d9072ab-34ba-4776-af50-3ec76dfc8eb8" class="wlWriterEditableSmartContent"&gt;&lt;div id="6c719ead-211b-4239-83de-8c1619c58481" style="margin: 0px; padding: 0px; display: inline;"&gt;&lt;div&gt;&lt;a href="http://www.youtube.com/watch?v=wmeUwzFGoHk" target="_new"&gt;&lt;img src="http://lh5.ggpht.com/_GaS6iHPgjYA/Sy-exIitZsI/AAAAAAAALeA/DCoC-kz1Gtw/videoa2d4ab00a67d%5B6%5D.jpg?imgmax=800" style="border-style: none" galleryimg="no" onload="var downlevelDiv = document.getElementById('6c719ead-211b-4239-83de-8c1619c58481'); downlevelDiv.innerHTML = &amp;quot;&amp;lt;div&amp;gt;&amp;lt;object width=\&amp;quot;425\&amp;quot; height=\&amp;quot;355\&amp;quot;&amp;gt;&amp;lt;param name=\&amp;quot;movie\&amp;quot; value=\&amp;quot;http://www.youtube.com/v/wmeUwzFGoHk&amp;amp;hl=en\&amp;quot;&amp;gt;&amp;lt;\/param&amp;gt;&amp;lt;embed src=\&amp;quot;http://www.youtube.com/v/wmeUwzFGoHk&amp;amp;hl=en\&amp;quot; type=\&amp;quot;application/x-shockwave-flash\&amp;quot; width=\&amp;quot;425\&amp;quot; height=\&amp;quot;355\&amp;quot;&amp;gt;&amp;lt;\/embed&amp;gt;&amp;lt;\/object&amp;gt;&amp;lt;\/div&amp;gt;&amp;quot;;" alt=""&gt;&lt;/a&gt;&lt;/div&gt;&lt;/div&gt;&lt;/div&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-6523658624898108946?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/6523658624898108946/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=6523658624898108946' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/6523658624898108946'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/6523658624898108946'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2009/12/gpu-perlin-noise.html' title='GPU Perlin Noise'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh6.ggpht.com/_GaS6iHPgjYA/Sy-Uwn3Yh3I/AAAAAAAALdQ/y8EvtX3b3vM/s72-c/Uhhh_thumb.jpg?imgmax=800' height='72' width='72'/><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-5935572383438353559</id><published>2009-12-09T18:38:00.001Z</published><updated>2009-12-09T19:25:43.097Z</updated><title type='text'>Procedural LOD Planet Textures</title><content type='html'>&lt;p&gt;I got a rough draft of procedural LOD planet textures working and thought I’d share some screenshots. The main difference between this and the last post is that this planet subdivides its patches and generates a new texture for each new patch as the camera gets closer and the planet in the last post was just static (it only generated vertices and textures at start up). Currently, all the textures are created in software so it’s hella slow, too slow to play really. Once a texture is generated and cached it’s very fast (capped at 60fps). On-the-fly however even with a texture size of only 17x17 pixels (same amount of vertices per patch) it’s jerky. Here are 6 levels of 256x256 textures zooming in on the one spot.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/_GaS6iHPgjYA/Sx_uiFEY0LI/AAAAAAAALa0/uqqbua9sfMQ/s1600-h/ProceduralTextureLevel0%5B2%5D.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="ProceduralTextureLevel0" border="0" alt="ProceduralTextureLevel0" src="http://lh4.ggpht.com/_GaS6iHPgjYA/Sx_ujPJwVTI/AAAAAAAALbA/aDRpZySksIY/ProceduralTextureLevel0_thumb.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh5.ggpht.com/_GaS6iHPgjYA/Sx_ukWFUODI/AAAAAAAALbM/H4AyAxxUIaw/s1600-h/ProceduralTextureLevel1%5B2%5D.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="ProceduralTextureLevel1" border="0" alt="ProceduralTextureLevel1" src="http://lh4.ggpht.com/_GaS6iHPgjYA/Sx_ulYN_S2I/AAAAAAAALbY/Sn94Kkip9KM/ProceduralTextureLevel1_thumb.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh3.ggpht.com/_GaS6iHPgjYA/Sx_umbMaQYI/AAAAAAAALbk/CI78XrS2FjM/s1600-h/ProceduralTextureLevel2%5B2%5D.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="ProceduralTextureLevel2" border="0" alt="ProceduralTextureLevel2" src="http://lh6.ggpht.com/_GaS6iHPgjYA/Sx_unjDIScI/AAAAAAAALbw/obA1Z-F8aNg/ProceduralTextureLevel2_thumb.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh3.ggpht.com/_GaS6iHPgjYA/Sx_uopvtgHI/AAAAAAAALb8/Sb3QTyAhTow/s1600-h/ProceduralTextureLevel3%5B2%5D.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="ProceduralTextureLevel3" border="0" alt="ProceduralTextureLevel3" src="http://lh5.ggpht.com/_GaS6iHPgjYA/Sx_up1PW6kI/AAAAAAAALcI/i1K06asMB3A/ProceduralTextureLevel3_thumb.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh3.ggpht.com/_GaS6iHPgjYA/Sx_urCHv9WI/AAAAAAAALcU/d_2i2rrKEYk/s1600-h/ProceduralTextureLevel4%5B2%5D.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="ProceduralTextureLevel4" border="0" alt="ProceduralTextureLevel4" src="http://lh3.ggpht.com/_GaS6iHPgjYA/Sx_usV3C42I/AAAAAAAALcg/LEyTZQHULqg/ProceduralTextureLevel4_thumb.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh6.ggpht.com/_GaS6iHPgjYA/Sx_utb0VnaI/AAAAAAAALcs/6NzPgHLYrRA/s1600-h/ProceduralTextureLevel5%5B2%5D.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="ProceduralTextureLevel5" border="0" alt="ProceduralTextureLevel5" src="http://lh3.ggpht.com/_GaS6iHPgjYA/Sx_uuYci3qI/AAAAAAAALc4/P1l5AYTch-E/ProceduralTextureLevel5_thumb.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;Next steps are to try to speed it up so it’s acceptable to play with, so I’ll probably do 2 things; use &lt;a href="http://www.eqatec.com/tools/profiler"&gt;EQATEC&lt;/a&gt; to profile my app and do the image generation in hardware. But before I do that, I somehow messed up the geometry so it’s clockwise instead of anti-clockwise… or the other way around… whatever I did anyways I’ll try to undo.&lt;/p&gt;  &lt;p&gt;&lt;font color="#ff0000"&gt;Update:&lt;/font&gt; Here’s a video, fraps and windows movie maker seem to work well with youtube, my previous efforts at uploading video turned out horrible! I’m only running the textures at 17x17 so the video runs smoothly (i.e. I know it looks like a big steaming pile of sh!t).&lt;/p&gt;  &lt;div style="padding-bottom: 0px; padding-left: 0px; width: 425px; padding-right: 0px; display: block; float: none; margin-left: auto; margin-right: auto; padding-top: 0px" id="scid:5737277B-5D6D-4f48-ABFC-DD9C333F4C5D:14d9c375-a1bb-4f6f-93a3-7db55a139328" class="wlWriterEditableSmartContent"&gt;&lt;div id="4d13adef-6f8a-49c3-82b2-a93d5732c263" style="margin: 0px; padding: 0px; display: inline;"&gt;&lt;div&gt;&lt;a href="http://www.youtube.com/watch?v=FLbACtoXu8k" target="_new"&gt;&lt;img src="http://lh4.ggpht.com/_GaS6iHPgjYA/Sx_5tc0jgJI/AAAAAAAALdE/-lGzYBUmIm0/videoc8c1146fd5fd%5B3%5D.jpg?imgmax=800" style="border-style: none" galleryimg="no" onload="var downlevelDiv = document.getElementById('4d13adef-6f8a-49c3-82b2-a93d5732c263'); downlevelDiv.innerHTML = &amp;quot;&amp;lt;div&amp;gt;&amp;lt;object width=\&amp;quot;425\&amp;quot; height=\&amp;quot;355\&amp;quot;&amp;gt;&amp;lt;param name=\&amp;quot;movie\&amp;quot; value=\&amp;quot;http://www.youtube.com/v/FLbACtoXu8k&amp;amp;hl=en\&amp;quot;&amp;gt;&amp;lt;\/param&amp;gt;&amp;lt;embed src=\&amp;quot;http://www.youtube.com/v/FLbACtoXu8k&amp;amp;hl=en\&amp;quot; type=\&amp;quot;application/x-shockwave-flash\&amp;quot; width=\&amp;quot;425\&amp;quot; height=\&amp;quot;355\&amp;quot;&amp;gt;&amp;lt;\/embed&amp;gt;&amp;lt;\/object&amp;gt;&amp;lt;\/div&amp;gt;&amp;quot;;" alt=""&gt;&lt;/a&gt;&lt;/div&gt;&lt;/div&gt;&lt;/div&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-5935572383438353559?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/5935572383438353559/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=5935572383438353559' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/5935572383438353559'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/5935572383438353559'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2009/12/procedural-lod-planet-textures.html' title='Procedural LOD Planet Textures'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh4.ggpht.com/_GaS6iHPgjYA/Sx_ujPJwVTI/AAAAAAAALbA/aDRpZySksIY/s72-c/ProceduralTextureLevel0_thumb.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-4300775691004668094</id><published>2009-12-07T21:55:00.001Z</published><updated>2009-12-08T15:22:18.836Z</updated><title type='text'>Seams Like Years…</title><content type='html'>&lt;p&gt;It’s been a while since I updated this… a really long while, but I’m going to try to get back into it again. My current problem is something I never really fixed the last time: seams. Here’s an example:&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh3.ggpht.com/_GaS6iHPgjYA/Sx15vOd5s3I/AAAAAAAALZI/2F65oYw89LI/s1600-h/Seams%5B9%5D.jpg"&gt;&lt;img style="border-right-width: 0px; display: block; float: none; border-top-width: 0px; border-bottom-width: 0px; margin-left: auto; border-left-width: 0px; margin-right: auto" title="Seams" border="0" alt="Seams" src="http://lh3.ggpht.com/_GaS6iHPgjYA/Sx15we5Yy8I/AAAAAAAALZM/sgR9MyLgZPE/Seams_thumb%5B7%5D.jpg?imgmax=800" width="500" height="379" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;Weirdly enough if I save the textures I generate for the faces they line up fine with no seam (the darkish hole should line up with the pit above):&lt;/p&gt;  &lt;p&gt;&lt;a href="http://lh4.ggpht.com/_GaS6iHPgjYA/Sx15xVld5-I/AAAAAAAALZQ/kWwKdNgyNx0/s1600-h/NoSeamsOnLeftBackAndRightTextures%5B5%5D.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="NoSeamsOnLeftBackAndRightTextures" border="0" alt="NoSeamsOnLeftBackAndRightTextures" src="http://lh3.ggpht.com/_GaS6iHPgjYA/Sx15ycw0oGI/AAAAAAAALZU/ROXYcAkpUG8/NoSeamsOnLeftBackAndRightTextures_thumb%5B3%5D.jpg?imgmax=800" width="500" height="177" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;So, having changed my texture generator around a bit I’m 100% sure it’s &lt;strike&gt;my texture code&lt;/strike&gt; &lt;strike&gt;some sort of floating point error&lt;/strike&gt; how MDX is texturing the faces. There must be a way to get MDX to just display the bitmap I give it &amp;amp; not mess up the edges…&lt;/p&gt;  &lt;p&gt;&lt;font color="#ff0000"&gt;Update 1:&lt;/font&gt; I had some mag &amp;amp; min filtering going on which was causing some (but not all of my seam problems. When I got rid of this code:&lt;/p&gt;  &lt;pre class="code"&gt;&lt;span style="color: green"&gt;&lt;font size="1"&gt;//    device.SamplerState[0].MinFilter = Direct3D.TextureFilter.Anisotropic;&lt;br /&gt;//    device.SamplerState[0].MagFilter = Direct3D.TextureFilter.Anisotropic;&lt;/font&gt;&lt;/span&gt;&lt;/pre&gt;&lt;br /&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;It looks like this now (still a problem with top and bottom patches but going from front to left to back to right and back is seamless now):&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;a href="http://lh6.ggpht.com/_GaS6iHPgjYA/Sx2LDXtLUII/AAAAAAAALZg/yO2l3SlJ4mE/s1600-h/FilterSeamsFixed%5B4%5D.jpg"&gt;&lt;img style="border-right-width: 0px; display: block; float: none; border-top-width: 0px; border-bottom-width: 0px; margin-left: auto; border-left-width: 0px; margin-right: auto" title="FilterSeamsFixed" border="0" alt="FilterSeamsFixed" src="http://lh3.ggpht.com/_GaS6iHPgjYA/Sx2LESIsWPI/AAAAAAAALZk/86c6ZlUyhHg/FilterSeamsFixed_thumb%5B2%5D.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;Not sure what’s causing it, but you can see from front to top to back to bottom the textures I’m generating seem to be slightly offset – the image on the right offsets them in the correct direction and they seem to match much better.&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p align="center"&gt;&lt;a href="http://lh4.ggpht.com/_GaS6iHPgjYA/Sx2LFDMWPYI/AAAAAAAALZo/oPEyxLmj9mE/s1600-h/nooffset%5B3%5D.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="nooffset" border="0" alt="nooffset" src="http://lh4.ggpht.com/_GaS6iHPgjYA/Sx2LGNt2J-I/AAAAAAAALZs/5CA-J2YDxFY/nooffset_thumb%5B1%5D.jpg?imgmax=800" width="200" height="798" /&gt;&lt;/a&gt; &lt;a href="http://lh6.ggpht.com/_GaS6iHPgjYA/Sx2LHLscf_I/AAAAAAAALZ0/qF1zv9mEB0c/s1600-h/offset%5B3%5D.jpg"&gt;&lt;img style="border-right-width: 0px; display: inline; border-top-width: 0px; border-bottom-width: 0px; border-left-width: 0px" title="offset" border="0" alt="offset" src="http://lh5.ggpht.com/_GaS6iHPgjYA/Sx2LIPQ3ICI/AAAAAAAALZ4/EUQDydLhbTE/offset_thumb%5B1%5D.jpg?imgmax=800" width="200" height="798" /&gt;&lt;/a&gt;&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;font color="#ff0000"&gt;Update 2:&lt;/font&gt; There were some errors in how I collated the heights from sub-patches, now top to bottom match up perfectly, and I have no seams!&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;a href="http://lh5.ggpht.com/_GaS6iHPgjYA/Sx5vGuN88zI/AAAAAAAALaE/QG_gpwiMiWM/s1600-h/NoSeams%5B12%5D.jpg"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="NoSeams" border="0" alt="NoSeams" src="http://lh6.ggpht.com/_GaS6iHPgjYA/Sx5vH-Nws3I/AAAAAAAALaQ/ZzgCIWIa2NQ/NoSeams_thumb%5B10%5D.jpg?imgmax=800" width="500" height="375" /&gt;&lt;/a&gt; &lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p align="center"&gt;&lt;a href="http://lh3.ggpht.com/_GaS6iHPgjYA/Sx5vJLBUgEI/AAAAAAAALac/P9prjB7rOvc/s1600-h/NoSeamsTextures%5B3%5D.jpg"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="NoSeamsTextures" border="0" alt="NoSeamsTextures" src="http://lh3.ggpht.com/_GaS6iHPgjYA/Sx5vKYPfddI/AAAAAAAALao/q7FVgpMqZY0/NoSeamsTextures_thumb%5B1%5D.jpg?imgmax=800" width="200" height="798" /&gt;&lt;/a&gt; &lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;Next back to the adaptive planet (the one that properly changes its patches depending on LOD) and an attempt at making the textures in hardware.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-4300775691004668094?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/4300775691004668094/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=4300775691004668094' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/4300775691004668094'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/4300775691004668094'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2009/12/seams-like-years.html' title='Seams Like Years…'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh3.ggpht.com/_GaS6iHPgjYA/Sx15we5Yy8I/AAAAAAAALZM/sgR9MyLgZPE/s72-c/Seams_thumb%5B7%5D.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-2295565988333358551</id><published>2008-09-24T00:42:00.001+01:00</published><updated>2008-09-24T00:42:02.776+01:00</updated><title type='text'>Stochastic LSystems</title><content type='html'>&lt;p&gt;I don't have much of an excuse for not working on this poor project and it's withering blog.&amp;nbsp; Work's gotten really busy but also I've gotten interested in a few other side projects (I want to build myself a &lt;a href="http://monome.org/" target="_blank"&gt;monome&lt;/a&gt; &amp;amp; I want to do &lt;a href="http://www.cs.cmu.edu/~johnny/projects/wii/" target="_blank"&gt;these Wii hacks&lt;/a&gt;)... I'm hoping to bring the new stuff into this project somehow so that it doesn't call social welfare on me for neglect... and if it does I hope it doesn't walk into another door or fall down the stairs again.&lt;/p&gt; &lt;p&gt;A very simple change to where I left off was to introduce a bit of randomness to the L-System so that not all plants look the same. The only difference between a normal L-System and a Stochastic one is that with the stochastic one there's a certain probability of each production rule being applied.&amp;nbsp; So now the plants appear in all sorts of shapes and sizes but still plant-like:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SNl-mjptUWI/AAAAAAAAAaE/H00Ep5ymPiE/s1600-h/stochasticmedweed2%5B2%5D.jpg"&gt;&lt;img height="180" alt="stochasticmedweed2" src="http://lh3.ggpht.com/john.leonard.ireland/SNl-nZSARhI/AAAAAAAAAaI/WvLfS0IVwJk/stochasticmedweed2_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SNl-p1ClWjI/AAAAAAAAAaM/9p840t9_zkk/s1600-h/stochasticmedweed%5B2%5D.jpg"&gt;&lt;img height="180" alt="stochasticmedweed" src="http://lh3.ggpht.com/john.leonard.ireland/SNl-qzVmtdI/AAAAAAAAAaQ/A3WWOBtdPxw/stochasticmedweed_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh4.ggpht.com/john.leonard.ireland/SNl-trsw-jI/AAAAAAAAAaU/ditdaqXxnGQ/s1600-h/stochasticbigweed%5B2%5D.jpg"&gt;&lt;img height="180" alt="stochasticbigweed" src="http://lh6.ggpht.com/john.leonard.ireland/SNl-vQJLrSI/AAAAAAAAAaY/PCbtfOlqSlM/stochasticbigweed_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh4.ggpht.com/john.leonard.ireland/SNl-xJyiKUI/AAAAAAAAAac/RA0_Eg73ftY/s1600-h/stocasticsmallweed%5B2%5D.jpg"&gt;&lt;img height="180" alt="stocasticsmallweed" src="http://lh4.ggpht.com/john.leonard.ireland/SNl-yFB6FnI/AAAAAAAAAag/bbTjPy6wKEk/stocasticsmallweed_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;In order to show the 3D-ness of them all I arranged a few plants in a grid and tried to record a fly-about.&amp;nbsp; Unfortunately it wasn't smooth at all (I've only a track-pad - I'll get a mouse soon) so I put a bit of velocity into the camera movements so that the camera keeps going whatever direction I pushed in. I tried to move about randomly in time with whatever music I had on in the background.&amp;nbsp; It's hard to describe but it was really really fun - I was terrible at it and messed up so many takes spinning out of control into yellowness.&lt;/p&gt; &lt;p&gt;I got a couple of decent takes (relatively speaking), but when I try to compress it for youtube it turns out all jerky and crappy so I might give it another bash tomorrow and update this post.&amp;nbsp; &lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-2295565988333358551?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/2295565988333358551/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=2295565988333358551' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/2295565988333358551'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/2295565988333358551'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/09/stochastic-lsystems.html' title='Stochastic LSystems'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh3.ggpht.com/john.leonard.ireland/SNl-nZSARhI/AAAAAAAAAaI/WvLfS0IVwJk/s72-c/stochasticmedweed2_thumb.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-5569674452036946644</id><published>2008-07-25T18:55:00.001+01:00</published><updated>2008-07-25T18:55:50.325+01:00</updated><title type='text'>L-Systems in 3D (lines)</title><content type='html'>&lt;p&gt;It's been WAY too long since I updated this, I'd like to say I've been doing more important things like saving the world or something, but nope, nothing.&amp;nbsp; I've spent most of my free time addicted to a game called &lt;a href="http://www.elderscrolls.com/games/oblivion_overview.htm" target="_blank"&gt;Oblivion&lt;/a&gt;, it's a great game.&amp;nbsp; I guess you could say I have been doing some good by saving the good citizens of &lt;a href="http://www.uesp.net/wiki/Tamriel:Cyrodiil" target="_blank"&gt;Cyrodiil&lt;/a&gt;.&amp;nbsp; Although... that's not strictly true, I murdered a good few of them.&amp;nbsp; To make it seem like I wasn't just playing a game all the time let's just say I was doing research...&lt;/p&gt; &lt;p&gt;I'll be away from the XBox while I'm back in Ireland so I decided to pick up where I left off so I migrated the L-System stuff I had in the WPF test project over to my DirectX project.&amp;nbsp; It was pretty easy, here's the fractal plant in 2D but in the DirectX app.&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SIoTlij-lqI/AAAAAAAAAZ8/PmmhAUXNEbc/s1600-h/lsystemFractalPlantInDX%5B3%5D.jpg"&gt;&lt;img height="350" alt="lsystemFractalPlantInDX" src="http://lh3.ggpht.com/john.leonard.ireland/SIoTo6dVa0I/AAAAAAAAAaA/0dM26HjZKvg/lsystemFractalPlantInDX_thumb%5B1%5D.jpg?imgmax=800" width="462"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;I then wrote a turtle-graphics class that would traverse the L-System's result and draw in 3D.&amp;nbsp; The result is still pretty flat because it's just lines and a picture doesn't really do it justice, so I uploaded a video to show what it looks like:&lt;/p&gt; &lt;p align="center"&gt;&lt;embed src="http://www.youtube.com/v/leB966vG9k8" width="425" height="350" type="application/x-shockwave-flash"&gt; &lt;/embed&gt;&lt;/p&gt; &lt;p&gt;I'm not sure what I should do next... but I think I'll have a go at making the 3D turtle graphics construct a polygon model from the L-System output instead of a line-model.&amp;nbsp; It doesn't get me any closer to procedural cities but it'd be cool to have procedural trees.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-5569674452036946644?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/5569674452036946644/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=5569674452036946644' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/5569674452036946644'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/5569674452036946644'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/07/l-systems-in-3d-lines.html' title='L-Systems in 3D (lines)'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh3.ggpht.com/john.leonard.ireland/SIoTo6dVa0I/AAAAAAAAAaA/0dM26HjZKvg/s72-c/lsystemFractalPlantInDX_thumb%5B1%5D.jpg?imgmax=800' height='72' width='72'/><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-1614354598483238123</id><published>2008-06-13T00:32:00.001+01:00</published><updated>2008-06-13T00:32:16.553+01:00</updated><title type='text'>L-Systems</title><content type='html'>&lt;p&gt;I spent some spare time today doing a first draft at an &lt;a href="http://en.wikipedia.org/wiki/L-system" target="_blank"&gt;L-System&lt;/a&gt;.&amp;nbsp; I was always intrigued by how nature is apparently governed by mathematics like the &lt;a href="http://en.wikipedia.org/wiki/Fibonacci_number#Fibonacci_numbers_in_nature" target="_blank"&gt;Fibonacci&lt;/a&gt; sequence.&amp;nbsp; L-Systems are basically grammars used commonly to model growth as it occurs in nature and to develop self-similar fractals.&amp;nbsp; A stochastic L-System (an L-System where each possible change has a certain probability of being selected) is what was used in this &lt;a href="http://graphics.ethz.ch/Downloads/Publications/Papers/2001/p_Par01.pdf" target="_blank"&gt;procedural cities paper&lt;/a&gt; for SIGGRAPH 2001.&amp;nbsp; There are some &lt;a href="http://www.gamesitb.com/SurveyProcedural.pdf" target="_blank"&gt;other methods&lt;/a&gt;, but I don't think they are as realistic as what Mueller and Pascal had done.&amp;nbsp; The L-System (with some add-on rules) is used to draw out the streets and also to generate buildings with different LODs.&amp;nbsp; I'm not sure where to go from my basic random-blocks-on-a-plane so I decided to look into L-Systems to try and generate a realistic city.&amp;nbsp; But first things first, here's a fractal plant (L-Systems in WPF):&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SFGx9l8_uQI/AAAAAAAAAZs/TP7bK4jLFvA/s1600-h/lsystemFractalPlant%5B3%5D.jpg"&gt;&lt;img height="310" alt="lsystemFractalPlant" src="http://lh4.ggpht.com/john.leonard.ireland/SFGx-SkpMsI/AAAAAAAAAZw/ItisKyV8Cl8/lsystemFractalPlant_thumb%5B1%5D.jpg?imgmax=800" width="300"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;I coded a basic L-System and &lt;a href="http://www.math.okstate.edu/mathdept/dynamics/lecnotes/node18.html#SECTION00046000000000000000" target="_blank"&gt;turtle graphics&lt;/a&gt; (something that draws whatever the L-System generates by following it like a path) and got the grammar for the plant on the &lt;a href="http://en.wikipedia.org/wiki/L-system#Example_8:_Fractal_plant" target="_blank"&gt;wiki page&lt;/a&gt;.&amp;nbsp; It looks very like something you'd find in nature, but it all follows a strict grammar with only 2 rules and if you look for it, you can see the self-similar patterns.&amp;nbsp; It does take a while to execute however, especially at high iterations.&amp;nbsp; &lt;a href="http://ejad.best.vwh.net/java/fractals/lsystems.shtml" target="_blank"&gt;This site&lt;/a&gt; has a few of the common L-System grammars in a java app so you can play about with different grammars/iterations etc. and &lt;a href="http://fractint.oblivion.cz/" target="_blank"&gt;here's&lt;/a&gt; a gallery of other simple fractal forms.&amp;nbsp; Here's one more from my little app before I hit the hay - an arty close-up of part of a Koch snowflake:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SFGx_Yg4u5I/AAAAAAAAAZ0/mbXQN2dNvIo/s1600-h/lsystemKochSnowflake%5B4%5D.jpg"&gt;&lt;img height="300" alt="lsystemKochSnowflake" src="http://lh4.ggpht.com/john.leonard.ireland/SFGx_w7D87I/AAAAAAAAAZ4/Cd_LUfcHfVY/lsystemKochSnowflake_thumb%5B2%5D.jpg?imgmax=800" width="300"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;I'll be honest, it's not arty, what it is is it's too fecking late to be messing about with WPF is what it is so screw you! Goodnight.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-1614354598483238123?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/1614354598483238123/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=1614354598483238123' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/1614354598483238123'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/1614354598483238123'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/06/l-systems.html' title='L-Systems'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh4.ggpht.com/john.leonard.ireland/SFGx-SkpMsI/AAAAAAAAAZw/ItisKyV8Cl8/s72-c/lsystemFractalPlant_thumb%5B1%5D.jpg?imgmax=800' height='72' width='72'/><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-8317540010334786392</id><published>2008-06-10T13:06:00.001+01:00</published><updated>2008-06-10T13:06:18.876+01:00</updated><title type='text'>Sharing is a bad thing</title><content type='html'>&lt;p&gt;I took a bit of time out to do some performance testing, partly avoiding procedural cities as I haven't a clue how to go forward but mainly to see what could cause my planet to be so slow when rendering a pretty low amount of polys.&amp;nbsp; I created a new project and ran some tests to get a benchmark, here are results for one patch getting larger as time goes on:&lt;/p&gt; &lt;p&gt;&amp;nbsp;&lt;img height="292" alt="performanceFpsSucksForSharedBuffer" src="http://lh5.ggpht.com/john.leonard.ireland/SE5uL187_ZI/AAAAAAAAAZc/OuNvCNiNnas/performanceFpsSucksForSharedBuffer_thumb%5B3%5D.jpg?imgmax=800" width="480"&gt;&lt;/p&gt; &lt;p&gt;Sharing the one vertex buffer is pretty much worse than having no vertex buffer at all!&amp;nbsp; I tried to see if 50 objects each with their own buffers vs. each sharing the one buffer would make any difference, but nope:&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SE5uMysNKBI/AAAAAAAAAZg/aleJXybC3pI/s1600-h/performanceFpsSucksForSharedBuffer%5B5%5D.jpg"&gt;&lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SE5uN_OQmaI/AAAAAAAAAZk/sfKnb1YHOjA/s1600-h/performanceFpsSucksFor50ObjectsWithSharedBuffer%5B4%5D.jpg"&gt;&lt;img height="321" alt="performanceFpsSucksFor50ObjectsWithSharedBuffer" src="http://lh5.ggpht.com/john.leonard.ireland/SE5uOXT5SnI/AAAAAAAAAZo/nm4-miPuSoM/performanceFpsSucksFor50ObjectsWithSharedBuffer_thumb%5B2%5D.jpg?imgmax=800" width="480"&gt;&lt;/a&gt;&lt;/a&gt;&amp;nbsp;&lt;/p&gt; &lt;p&gt;Weirdly enough though, 75% of all pie-charts look like pac-man:&lt;/p&gt; &lt;p align="center"&gt;&lt;img height="308" src="http://www.usablemarkets.com/images/pie_pacman_chart.png" width="480"&gt; &lt;/p&gt; &lt;p align="left"&gt;Creating and deleting buffers on the fly for the planet just won't work as I found with earlier experiments with quadtrees.&amp;nbsp; Although I did find out that the garbage collector can't clean up buffers because behind the scenes a load of events are hooked up and these all have references to the buffer.&amp;nbsp; Setting Device.IsUsingEventHandlers to false can turn this off.&lt;/p&gt; &lt;p align="left"&gt;Sharing isn't efficient either.&amp;nbsp; A bunch of buffers will have to be created on startup to be exclusively used by each patch.&amp;nbsp; Working out how many and what size will be another performance analysis job... is it simple enough that I can keep procrastinating procedural cities? ... probably not.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-8317540010334786392?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/8317540010334786392/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=8317540010334786392' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/8317540010334786392'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/8317540010334786392'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/06/sharing-is-bad-thing.html' title='Sharing is a bad thing'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh5.ggpht.com/john.leonard.ireland/SE5uL187_ZI/AAAAAAAAAZc/OuNvCNiNnas/s72-c/performanceFpsSucksForSharedBuffer_thumb%5B3%5D.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-1619396692467492795</id><published>2008-06-05T16:37:00.001+01:00</published><updated>2008-06-05T16:37:03.849+01:00</updated><title type='text'>Welcome to Randomville</title><content type='html'>&lt;p&gt;I had a quick bash at doing a procedural city with some very basic ideas I had - it's really simple but already looks city-like.&amp;nbsp; Check it out.&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SEgH6E7A-yI/AAAAAAAAAY8/x5otRWlyj54/s1600-h/randomVille%5B2%5D.jpg"&gt;&lt;img height="180" alt="randomVille" src="http://lh5.ggpht.com/john.leonard.ireland/SEgH7E7A-zI/AAAAAAAAAZA/5qrOV2HPb3I/randomVille_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SEgH8U7A-0I/AAAAAAAAAZE/StS-OqtYQuc/s1600-h/randomVilleRooftop%5B2%5D.jpg"&gt;&lt;img height="180" alt="randomVilleRooftop" src="http://lh5.ggpht.com/john.leonard.ireland/SEgH9E7A-1I/AAAAAAAAAZI/4FoKaejHkqw/randomVilleRooftop_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;You can probably tell from looking at the images but all I'm doing is creating a grid of Mesh.Box(es) with random heights - biasing the height of boxes in the centre to be higher than the boxes on the outskirts.&amp;nbsp; This image might show it a little more clearly.&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SEgIAE7A-2I/AAAAAAAAAZM/cYjsCGPYkgY/s1600-h/randomVilleGrid%5B3%5D.jpg"&gt;&lt;img height="371" alt="randomVilleGrid" src="http://lh6.ggpht.com/john.leonard.ireland/SEgICU7A-3I/AAAAAAAAAZQ/b9QA5kyYncw/randomVilleGrid_thumb%5B1%5D.jpg?imgmax=800" width="489"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;In the next image I randomly eliminated some of the boxes (biasing the elimination more towards the edge than towards the centre).&amp;nbsp; I think it looks a little more realistic.&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SEgIEk7A-4I/AAAAAAAAAZU/n5obEYz9pWA/s1600-h/randomVilleUrbanRenewal%5B3%5D.jpg"&gt;&lt;img height="370" alt="randomVilleUrbanRenewal" src="http://lh3.ggpht.com/john.leonard.ireland/SEgIHk7A-5I/AAAAAAAAAZY/1gt-fgRYUM8/randomVilleUrbanRenewal_thumb%5B1%5D.jpg?imgmax=800" width="488"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;Flying around the city really gives a better city-feeling than looking at a bunch of boxes.&amp;nbsp; I tried to record a video but I couldn't get a smooth flyover using my touchpad and my *ahem* skills.&amp;nbsp; It doesn't look too bad but I won't post it as I'd be worried if someone saw my flying skills they'd think I was planning another 9/11.&amp;nbsp; &lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-1619396692467492795?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/1619396692467492795/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=1619396692467492795' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/1619396692467492795'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/1619396692467492795'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/06/welcome-to-randomville.html' title='Welcome to Randomville'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh5.ggpht.com/john.leonard.ireland/SEgH7E7A-zI/AAAAAAAAAZA/5qrOV2HPb3I/s72-c/randomVille_thumb.jpg?imgmax=800' height='72' width='72'/><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-4245407324731023974</id><published>2008-05-30T16:22:00.001+01:00</published><updated>2008-05-30T16:22:31.934+01:00</updated><title type='text'>I've found the Bible!!</title><content type='html'>&lt;p&gt;No, not in that way, my head still vomits while spinning all the way around when I'm near a church.&amp;nbsp; I've gotten a book which has contributions from a lot of the researchers at the top of the procedural content generation field. It's called &lt;em&gt;&lt;a href="http://www.amazon.com/Texturing-Modeling-Procedural-Approach-Kaufmann/dp/1558608486"&gt;Texturing &amp;amp; Modeling: A Procedural Approach&lt;/a&gt;&lt;/em&gt;.&amp;nbsp; It's (expensive but) friggen awesome!&amp;nbsp; I was a bit worried it would be like a scientific journal -that is, just a collation of papers- but every concept is well explained and structured (and sometimes comes with a little bit of code).&amp;nbsp; I'm convinced &lt;a href="http://www.infinity-universe.com/"&gt;Infinity&lt;/a&gt; uses this book as a basis for his engine.&lt;/p&gt; &lt;p align="center"&gt;&lt;img height="480" src="http://teg02.homestead.com/files/Mojo03/Text_Mod.jpg" width="384"&gt; &lt;/p&gt; &lt;p&gt;I've had a rethink about how go about developing this game.&amp;nbsp; Instead of getting into great detail in one area then when I'm happy move on, I'm going to get something somewhat reasonable then move on.&amp;nbsp; Basically I want to quickly prototype the game and see what it's like, and afterwards spend time refining and polishing it.&amp;nbsp; Getting bogged down in details often led to the demise of a few of my previous projects.&amp;nbsp; I think I'd like to look at &lt;a href="http://graphics.ethz.ch/Downloads/Publications/Papers/2001/p_Par01.pdf"&gt;generating procedural cities next&lt;/a&gt;.&lt;/p&gt; &lt;p&gt;I've decided to use &lt;a href="http://del.icio.us/"&gt;del.icio.us&lt;/a&gt; to bookmark and organise (with tags) all my areas of research as I come across them on the internets.&amp;nbsp; My personal set of bookmarks is at &lt;a title="http://del.icio.us/jellyedwards" href="http://del.icio.us/jellyedwards"&gt;http://del.icio.us/jellyedwards&lt;/a&gt;, keep in mind I've only started to use del.icio.us and it also will contain tags for non-game-development areas of interest I have (like WPF, wiki-projects, &lt;a href="http://www.ted.com/"&gt;TED&lt;/a&gt;, music).&amp;nbsp; Incidentally, I've started another &lt;a href="http://nyomnyom.blogspot.com/"&gt;blog&lt;/a&gt; (nothing in it yet) for a food-based wiki-project.&amp;nbsp; I've no idea if it'll work out or not, so I might post whatever other wiki/web 2.0 (hate that name) ideas I have there.&lt;/p&gt; &lt;p&gt;I'm really enjoying researching &lt;a href="http://www.ted.com/talks/view/id/66"&gt;a&lt;/a&gt; bunch &lt;a href="http://www.ted.com/index.php/talks/view/id/198"&gt;of&lt;/a&gt; random &lt;a href="http://www.ted.com/index.php/talks/view/id/191"&gt;things&lt;/a&gt; but nothing's actually getting done so I've got to get back into it.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-4245407324731023974?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/4245407324731023974/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=4245407324731023974' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/4245407324731023974'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/4245407324731023974'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/05/i-found-bible.html' title='I&amp;#39;ve found the Bible!!'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-973821622807848757</id><published>2008-05-27T00:39:00.001+01:00</published><updated>2008-05-27T00:39:31.771+01:00</updated><title type='text'>Procedural Textures - Tile/Wrap</title><content type='html'>&lt;p&gt;I've decided to take a break from the planet geometry stuff to look into procedural textures.&amp;nbsp; I've already gotten a few free pre-generated textures which I used &lt;a href="http://jellyengine.blogspot.com/2008/04/planets-03-texture.html"&gt;in&lt;/a&gt; &lt;a href="http://jellyengine.blogspot.com/2008/03/seasons.html"&gt;earlier&lt;/a&gt; &lt;a href="http://jellyengine.blogspot.com/2008/03/terrain-texturing.html"&gt;posts&lt;/a&gt;, but the idea of generating everything procedurally really appeals to me for some reason.&amp;nbsp; My level of knowledge in this area is - like most other areas - minimal, but from doing some research I'm starting to get a feel for it.&amp;nbsp; The &lt;a href="http://www.scene.org/"&gt;demoscene&lt;/a&gt; is where most of my procedural texturing/modelling research ended up, and the &lt;a href="http://www.pouet.net/prod.php?which=33147"&gt;demos&lt;/a&gt; ... &lt;a href="http://www.pouet.net/prod.php?which=12821"&gt;are&lt;/a&gt; ... &lt;a href="http://www.theprodukkt.com/kkrieger"&gt;absolutely&lt;/a&gt; ... &lt;a href="http://www.theprodukkt.com/debris"&gt;amazing&lt;/a&gt;...&amp;nbsp; Then you find out that they (sometimes) managed to stuff all the code into an executable less than 64KB!!!&amp;nbsp; &lt;a href="http://www.infinity-universe.com/"&gt;Infinity&lt;/a&gt; is by far closest to my aspirations for this project, his work has incredible detailed planets in real time with all sorts of fancy effects.&amp;nbsp; One of my favourite images from his work compares &lt;a href="http://www.gamedev.net/community/forums/mod/journal/journal.asp?jn=263350&amp;amp;cmonth=12&amp;amp;cyear=2005"&gt;a NASA space shot to his generated planet (Dec 14th 2005)&lt;/a&gt;.&lt;/p&gt; &lt;p&gt;Back to the main topic though and for procedural textures I think the guys from &lt;a href="http://www.theprodukkt.com"&gt;the produkkt&lt;/a&gt; have got it nailed.&amp;nbsp; They have a free tool (that is, free to use the textures it generates not the actual code behind it) called &lt;a href="http://www.werkkzeug.com/"&gt;werkkzeug&lt;/a&gt; which demonstrates their method for creating realistic textures procedurally.&amp;nbsp; If you have any interest in this stuff you should definitely try out their &lt;a href="http://support.werkkzeug.com/3te/gettingstarted.html"&gt;tutorial&lt;/a&gt;.&amp;nbsp; I've seen &lt;a href="http://libnoise.sourceforge.net/examples/textures/index.html"&gt;other examples&lt;/a&gt; for procedural texture generation which are cool in principle but kinda limited.&amp;nbsp; I was really amazed that realistic textures like this rusty barrel can be done with a bit of Perlin noise and layering other effects.&amp;nbsp; It's just the tutorial though, the &lt;a href="http://www.werkkzeug.com/examples/texture_gallery"&gt;gallery&lt;/a&gt; has more impressive textures.&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SDtKDZjuEfI/AAAAAAAAAW4/JudWazGHj2k/s1600-h/werkkzeugProceduralBarrel%5B2%5D.jpg"&gt;&lt;img height="163" alt="werkkzeugProceduralBarrel" src="http://lh6.ggpht.com/john.leonard.ireland/SDtKEJjuEgI/AAAAAAAAAXA/1uU2oOUfIic/werkkzeugProceduralBarrel_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;So... If you checked out the links above, reading the next section where I talk about work I've accomplished is gonna kinda be like when you walk onto a intercontinental plane... First you see the first class seats and think "sweet!!" then move on to the business class and think "sure, it's not as nice as first class but it's still pretty sweet, economy can't be that bad"...&amp;nbsp; Then you finally end up behind a curtain in the economy section where there are babies screaming and chickens flapping about the place and everywhere smells of sweat and cheese.&lt;/p&gt; &lt;p&gt;Whilst still recoiling in shock and disgust - the stewardess moves you along to where you're really seated - the cargo section.&amp;nbsp; Welcome to the update of my work!&lt;/p&gt; &lt;p&gt;I redid my Perlin noise app in Windows Presentation Framework (WPF) - partly to start WPF and partly because I &lt;a href="http://blogs.msdn.com/jgalasyn/archive/2008/04/17/using-writeablebitmap-to-display-a-procedural-texture.aspx"&gt;heard&lt;/a&gt; it was faster than the unsafe pointer-bitmap stuff I was doing before.&amp;nbsp; There was a bit of a learning curve, but I'm pretty happy with the results - as an aside I'm ecstatic that WPF will be replacing ASP AJAX and javascript as that's my main job and it's more frustrating than &lt;strike&gt;Hugh Hefner without viagra&lt;/strike&gt; ... playing pool with a rope.&amp;nbsp; Here's the app:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SDtKF5juEhI/AAAAAAAAAXI/iDKSYQM7yrc/s1600-h/newWPFPerlinSandbox%5B3%5D.jpg"&gt;&lt;img height="344" alt="newWPFPerlinSandbox" src="http://lh4.ggpht.com/john.leonard.ireland/SDtKGpjuEiI/AAAAAAAAAXQ/yQRrKrbT1dQ/newWPFPerlinSandbox_thumb%5B1%5D.jpg?imgmax=800" width="480"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;My main goal was to create a tileable/wrappable Perlin noise function so that I can eventually seamlessly tile my procedural texture.&amp;nbsp; I followed the example at the bottom of &lt;a href="http://www.cs.cmu.edu/~mzucker/code/perlin-noise-math-faq.html"&gt;this article by Zucker&lt;/a&gt;, and it took a long time to sink in.&lt;/p&gt;&lt;pre class="code"&gt;&lt;span style="color: blue"&gt;public float &lt;/span&gt;GetTileableNoise(&lt;span style="color: blue"&gt;int &lt;/span&gt;x, &lt;span style="color: blue"&gt;int &lt;/span&gt;y)&lt;br /&gt;{&lt;br /&gt;    &lt;span style="color: blue"&gt;return &lt;/span&gt;(GetNoise(x, y)*(tileWidth - x)*(tileHeight - y) +&lt;br /&gt;            GetNoise(x - tileWidth, y)*(x)*(tileHeight - y) +&lt;br /&gt;            GetNoise(x - tileWidth, y - tileHeight)*(x)*(y) +&lt;br /&gt;            GetNoise(x, y - tileHeight)*(tileWidth - x)*(y))&lt;br /&gt;        / (tileWidth * tileHeight);&lt;br /&gt;}&lt;/pre&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;br /&gt;&lt;p align="center"&gt;&lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SDtKIJjuEjI/AAAAAAAAAXY/ciVr7AnVK0k/s1600-h/newWPFPerlinSandboxSeamless%5B3%5D.jpg"&gt;&lt;img height="344" alt="newWPFPerlinSandboxSeamless" src="http://lh6.ggpht.com/john.leonard.ireland/SDtKJJjuEkI/AAAAAAAAAXg/hkl0k6sxWuo/newWPFPerlinSandboxSeamless_thumb%5B1%5D.jpg?imgmax=800" width="480"&gt;&lt;/a&gt; &lt;/p&gt;&lt;br /&gt;&lt;p&gt;I'm convinced this code could be a lot better:&lt;/p&gt;&lt;br /&gt;&lt;ul&gt;&lt;br /&gt;&lt;li&gt;werkkzeug seems to create a tileable Perlin noise texture instantly while this code is hella slow&lt;/li&gt;&lt;br /&gt;&lt;li&gt;there are some ugly tiling effects (cross-mirror I calls it) with certain combinations of noise&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;&lt;p align="center"&gt;&lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SDtKKJjuElI/AAAAAAAAAXo/cftr8Ky7AXg/s1600-h/perlin%5B5%5D.jpg"&gt;&lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SDtKLJjuEmI/AAAAAAAAAXw/SmTPsX2aCHo/s1600-h/perlinNoTile%5B5%5D.jpg"&gt;&lt;img height="180" alt="perlinNoTile" src="http://lh5.ggpht.com/john.leonard.ireland/SDtKL5juEnI/AAAAAAAAAX4/OvChMNxzniY/perlinNoTile_thumb%5B1%5D.jpg?imgmax=800" width="180"&gt;&lt;/a&gt; becomes &lt;img height="180" alt="perlin" src="http://lh3.ggpht.com/john.leonard.ireland/SDtKMZjuEoI/AAAAAAAAAYA/UEEwjZE6XMQ/perlin_thumb%5B1%5D.jpg?imgmax=800" width="180"&gt;&lt;/a&gt;&amp;nbsp; &lt;/p&gt;&lt;br /&gt;&lt;p&gt;I'll carry on with noise and textures for the time being, trying to speed it up in various ways (move to hardware texture creation perhaps?) and maybe think about implementing a poor-man's werkkzeug to play with texture creation.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-973821622807848757?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/973821622807848757/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=973821622807848757' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/973821622807848757'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/973821622807848757'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/05/procedural-textures-tilewrap.html' title='Procedural Textures - Tile/Wrap'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh6.ggpht.com/john.leonard.ireland/SDtKEJjuEgI/AAAAAAAAAXA/1uU2oOUfIic/s72-c/werkkzeugProceduralBarrel_thumb.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-5561051718322150810</id><published>2008-05-24T16:22:00.001+01:00</published><updated>2008-05-24T16:43:06.706+01:00</updated><title type='text'>Neighhhhbours, everybody needs...</title><content type='html'>&lt;p&gt;...to-know-the-orientation-of-themselves-to-their neighhhhbours, that's when non-uniformly-laid-out neighbours, become good-at-preventing-cracking-due-to-different-levels-of-detail-and-also good friends.&lt;/p&gt; &lt;p&gt;Just as in the soap, my geomipmapped planet needs to take care when linking a patch to one of it's neighbours.&amp;nbsp; However, whereas the soap intended to create cracks between neighbours, my objective is the opposite.&amp;nbsp; Each patch at any level of detail is set up to have 4 children: top-left, top-right, bottom-left and bottom-right; and 4 neighbours: north, south, east and &lt;strike&gt;kylie&lt;/strike&gt; west.&amp;nbsp; This image (which I use as a texture for debugging) should make it clearer.&amp;nbsp; The text "back" at the centre is just so I know from which of the main cube faces (my sphere is really a &lt;a href="http://jellyengine.blogspot.com/2008/04/planets-01.html"&gt;subdivided cube&lt;/a&gt;) this patch comes from.&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SDgyYpjuEXI/AAAAAAAAAV4/TVa3a7diNZk/s1600-h/backDebugTexture%5B2%5D.jpg"&gt;&lt;img height="180" alt="backDebugTexture" src="http://lh3.ggpht.com/john.leonard.ireland/SDgyaJjuEYI/AAAAAAAAAWA/ojI8SjeD0o8/backDebugTexture_thumb.jpg?imgmax=800" width="180"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;The neighbours of the main faces of the cube are set up manually at the start, but they need a way to set up the neighbours of their children when they are subdivided.&amp;nbsp; The internal neighbour case is fairly trivial for when a patch subdivides:&lt;/p&gt; &lt;ul&gt; &lt;li&gt;east of the top left child is the top right child&lt;/li&gt; &lt;li&gt;west of the bottom right child is the bottom left child&lt;/li&gt; &lt;li&gt;north of the bottom left child is the top left child&lt;/li&gt; &lt;li&gt;south of the top right child is the bottom right child&amp;nbsp; &lt;/li&gt; &lt;li&gt;and so on...&lt;/li&gt;&lt;/ul&gt; &lt;p&gt;To get the external neighbours for its children a patch will have to look to its own neighbours, so:&lt;/p&gt; &lt;ul&gt; &lt;li&gt;east of the top right child is the top left child of the patch to the east&lt;/li&gt; &lt;li&gt;south of the bottom left child is the top left child of the patch to the south&lt;/li&gt; &lt;li&gt;and so on...&lt;/li&gt;&lt;/ul&gt; &lt;p&gt;This might perhaps be more obvious in the following diagrams where the level of detail goes up by one for the patch at the back of the cube.&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh4.ggpht.com/john.leonard.ireland/SDgycZjuEZI/AAAAAAAAAWI/Jnx-8byIhJY/s1600-h/backKids0%5B3%5D.jpg"&gt;&lt;img height="360" alt="backKids0" src="http://lh3.ggpht.com/john.leonard.ireland/SDgyeJjuEaI/AAAAAAAAAWQ/zQpjJtqCjxY/backKids0_thumb%5B1%5D.jpg?imgmax=800" width="480"&gt;&lt;/a&gt; &lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SDgyg5juEbI/AAAAAAAAAWY/VuzYsAukNeA/s1600-h/backKids1%5B3%5D.jpg"&gt;&lt;img height="360" alt="backKids1" src="http://lh6.ggpht.com/john.leonard.ireland/SDgyi5juEcI/AAAAAAAAAWg/EtcMkDcf0iI/backKids1_thumb%5B1%5D.jpg?imgmax=800" width="480"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;In the first image the top left child gets subdivided and it would set its own top right child to have the main patch's top right child's top left child as its eastern patch.&amp;nbsp; Confused?&amp;nbsp; Maybe this will help:&lt;/p&gt; &lt;p&gt;backPatch.topLeftChild.topRightChild.east = backPatch.topRightChild.topLeftChild;&lt;/p&gt; &lt;p&gt;This can be generalised to work recursively (assuming east is set up correctly) to:&lt;/p&gt; &lt;p&gt;patch.topRightChild.east = patch.east.topLeftChild;&lt;/p&gt; &lt;p&gt;Basically, for a child to find its external neighbour (a neighbour from outside its own family) it will have to look at its parents neighbours.&amp;nbsp; If a person wanted to find out their cousins, they would have to find the children of their parent's siblings.&lt;/p&gt; &lt;p&gt;Ok got it now?&amp;nbsp; I hope so, because I went through the same confusion only to find out it doesn't always work.&lt;/p&gt; &lt;p&gt;If you stand at the north pole of the earth, any direction you go in will be south.&amp;nbsp; This doesn't play too well with my north, south, east &amp;amp; west neighbour collection.&amp;nbsp; These 2 videos show the problem, if you set the main cube faces so that moving east to west is ok, moving north to south will be problematic (they look upside-down compared to each other).&amp;nbsp; You could fix it so north to south worked ok, but then east to west wouldn't work.&lt;/p&gt; &lt;p align="center"&gt; &lt;div class="wlWriterSmartContent" id="scid:5737277B-5D6D-4f48-ABFC-DD9C333F4C5D:565223aa-5d21-4a49-afbd-e15b241fde96" style="padding-right: 0px; display: inline; padding-left: 0px; float: none; padding-bottom: 0px; margin: 0px; padding-top: 0px"&gt;&lt;div&gt;&lt;object width="425" height="355"&gt;&lt;param name="movie" value="http://www.youtube.com/v/3fKV97yKAyQ"&gt;&lt;/param&gt;&lt;param name="wmode" value="transparent"&gt;&lt;/param&gt;&lt;embed src="http://www.youtube.com/v/3fKV97yKAyQ" type="application/x-shockwave-flash" wmode="transparent" width="425" height="355"&gt;&lt;/embed&gt;&lt;/object&gt;&lt;/div&gt;&lt;label style="font-size:.8em;"&gt;Moving east to west matches up&lt;/label&gt;&lt;/div&gt;&lt;/p&gt; &lt;p align="center"&gt; &lt;div class="wlWriterSmartContent" id="scid:5737277B-5D6D-4f48-ABFC-DD9C333F4C5D:4856b84e-f43f-444b-b27c-6133b972f025" style="padding-right: 0px; display: inline; padding-left: 0px; float: none; padding-bottom: 0px; margin: 0px; padding-top: 0px"&gt;&lt;div&gt;&lt;object width="425" height="355"&gt;&lt;param name="movie" value="http://www.youtube.com/v/-i-l4sWCM5I"&gt;&lt;/param&gt;&lt;param name="wmode" value="transparent"&gt;&lt;/param&gt;&lt;embed src="http://www.youtube.com/v/-i-l4sWCM5I" type="application/x-shockwave-flash" wmode="transparent" width="425" height="355"&gt;&lt;/embed&gt;&lt;/object&gt;&lt;/div&gt;&lt;label style="font-size:.8em;"&gt;Moving north to south shows up clashing patches&lt;/label&gt;&lt;/div&gt;&lt;/p&gt; &lt;p&gt;The video is a bit blurry, so here's an image highlighting the problem, it shows the where the front (A), right (B) and top (C) patches meet.&amp;nbsp; Because the top patch only has one south, it clashes with the right patch (if I go north from the B then go south again, instead of ending up back at B where I started - I end up on the front patch A).&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SDgyqJjuEdI/AAAAAAAAAWo/L7rdl9tW1VM/s1600-h/cornerNeighboursMarked%5B3%5D.jpg"&gt;&lt;img height="360" alt="cornerNeighboursMarked" src="http://lh4.ggpht.com/john.leonard.ireland/SDgytZjuEeI/AAAAAAAAAWw/u_t4tlEfcDA/cornerNeighboursMarked_thumb%5B1%5D.jpg?imgmax=800" width="480"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;This can cause cracking because neighbours aren't actually neighbours.&amp;nbsp; If the code for setting the top left's north was like this:&lt;/p&gt; &lt;p&gt;topLeft.north = north.bottomLeft;&lt;/p&gt; &lt;p&gt;For north neighbours, it would work for A to C but not for B to C.&amp;nbsp; For the case of B, north of topLeft is actually north.bottomRight.&amp;nbsp; B.topLeft should look at C.bottomRight when it's rendering otherwise it might try to fix a crack when it's not there or vice versa.&amp;nbsp; The solution is to look at the orientation of the current patch to the north patch, for example if this patch (B) is to the east of this patch's north (C) then topLeft.north = north.bottomRight.&amp;nbsp; I found it difficult to visualise what neighbours go where when I was writing the code to handle odd orientations so somewhat embarrassingly I cut out 2 bits of paper and used that to help.&lt;/p&gt; &lt;p&gt;Of course all of this is my own meandering implementation, there are much more elegant methods out there by people who know what they're doing (like &lt;a href="http://www.gamasutra.com/features/20010810/oneil_02.htm"&gt;Sean O'Neil's&lt;/a&gt;).&amp;nbsp; There isn't even a bit of crack to be seen with these neighbours, if only that were true of the &lt;a href="http://www.nowmagazine.co.uk/celebrity-news/242950/jason-donovan-cocaine-nearly-killed-me/1/"&gt;soap&lt;/a&gt;.&amp;nbsp; Next I'll do some clean-up with the code, and look at generating the base textures from scratch.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-5561051718322150810?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/5561051718322150810/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=5561051718322150810' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/5561051718322150810'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/5561051718322150810'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/05/neighhhhbours-everybody-needs.html' title='Neighhhhbours, everybody needs...'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh3.ggpht.com/john.leonard.ireland/SDgyaJjuEYI/AAAAAAAAAWA/ojI8SjeD0o8/s72-c/backDebugTexture_thumb.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-6502533688922176511</id><published>2008-05-21T20:38:00.001+01:00</published><updated>2008-05-21T20:38:33.576+01:00</updated><title type='text'>Planets 0.4.1 Cracks &amp; Holes</title><content type='html'>&lt;p&gt;I haven't blogged in a while, even though I've been tapping away at the code I'm afraid little progress has been made.&amp;nbsp; The main function I've been concentrating on creates a triangle list for a patch with respect to cracking and also holes or partial patches created by some but not all children being drawn.&amp;nbsp; I wouldn't say that I'm a neat coder but I do know when things get out of hand - I really don't know how I can make this function any simpler.&amp;nbsp; Because of this, I don't have much confidence in the code being bug free.&amp;nbsp; However last night it all seemed to come together:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SDR6MNSUF0I/AAAAAAAAAVY/MnGRl5JD8ZY/s1600-h/planetNoCracksHoles%5B4%5D.jpg"&gt;&lt;img height="341" alt="planetNoCracksHoles" src="http://lh4.ggpht.com/john.leonard.ireland/SDR6M9SUF1I/AAAAAAAAAVg/13NH_VR3QLI/planetNoCracksHoles_thumb%5B2%5D.jpg?imgmax=800" width="450"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;Until I saw this bastard hole at the bottom.&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SDR6NtSUF2I/AAAAAAAAAVo/uxJlFvZYLGg/s1600-h/planetGmmHole%5B4%5D.jpg"&gt;&lt;img height="341" alt="planetGmmHole" src="http://lh5.ggpht.com/john.leonard.ireland/SDR6ONSUF3I/AAAAAAAAAVw/9SMqkiwng6w/planetGmmHole_thumb%5B2%5D.jpg?imgmax=800" width="450"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;The thing is there are 56 (8 choose 2) different possible index layouts taking into consideration compensating for combinations of holes and cracking.&amp;nbsp; I should either (1) write an automated test for each of these combinations or (2) start over.&amp;nbsp; I've decided to be lazy and go for option 3, try to fix this one and hope it's the last.&amp;nbsp; But I will make a public promise here in my blog that if there's another anomaly after this one I'll write tests for each case.&lt;/p&gt; &lt;p&gt;Let's be honest, if that happens I'll go for option 4 and edit the blog not to have any promise of doing testing at all.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-6502533688922176511?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/6502533688922176511/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=6502533688922176511' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/6502533688922176511'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/6502533688922176511'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/05/planets-041-cracks-holes.html' title='Planets 0.4.1 Cracks &amp;amp; Holes'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh4.ggpht.com/john.leonard.ireland/SDR6M9SUF1I/AAAAAAAAAVg/13NH_VR3QLI/s72-c/planetNoCracksHoles_thumb%5B2%5D.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-6833275478137436184</id><published>2008-05-04T19:30:00.001+01:00</published><updated>2008-05-04T19:30:11.852+01:00</updated><title type='text'>Planets 0.4 - Geomipmapping</title><content type='html'>&lt;p&gt;I was avoiding doing this for so long, but in the end it's a really simple solution. It's a familiar problem, quad trees are great and all but they are really slow when you're trying to render a high detail (well at least the way I implemented them). Each quad has 9 vertices and renders by drawing a fan. &lt;a href="http://jellyengine.blogspot.com/2008/04/adaptive-quadtree.html"&gt;Previously&lt;/a&gt; I had given each quad its vertex and index buffer and this was a nightmare to clean up on program exit, it would just take AGES! I only found this out but it's no big hit to just share a vertex and index buffer between loads of patches just set the needed data before each render - the clean up is almost instant. So here's what a geomipmapped quad tree at level 8 looks like:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SB3_tg5OFiI/AAAAAAAAAUo/MnbnAAW_YJ0/s1600-h/gmmQuadPlanetLevel8%5B3%5D.jpg"&gt;&lt;img height="362" alt="gmmQuadPlanetLevel8" src="http://lh6.ggpht.com/john.leonard.ireland/SB3_7g5OFjI/AAAAAAAAAUw/tvisMucfsTQ/gmmQuadPlanetLevel8_thumb%5B1%5D.jpg?imgmax=800" width="477"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;It's only about 20,000 polygons but it's rendering at only 2 FPS, so unless I include sloths in my game demographic I'll have to improve on the speed. I thought the main problem stems from the fact that I'm doing about 2,500 renders of only 8 polygons in a fan and that it would be a lot faster as a triangle strip. I tried to think of algorithmic ways of aggregating all the vertices in a quad and rendering as a triangle strip - when blood started coming out of my ears I decided there must be a simpler way. So in the end the solution was a combination of (what I call) CLOD and quad trees - basically each quad tree patch can draw way more than just the 3 x 3 vertices in a fan, let each patch draw a triangle strip of (say) 17 x 17 vertices. This way I can reduce the levels needed to render a planet in high detail. Hopefully the next images will make this obvious:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh4.ggpht.com/john.leonard.ireland/SB4AIw5OFkI/AAAAAAAAAU4/5bYHapdUMBg/s1600-h/adaptiveNonaggregatedPlanet%5B2%5D.jpg"&gt;&lt;img height="180" alt="adaptiveNonaggregatedPlanet" src="http://lh4.ggpht.com/john.leonard.ireland/SB4ALw5OFlI/AAAAAAAAAVA/RW7HJu-LR0s/adaptiveNonaggregatedPlanet_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh4.ggpht.com/john.leonard.ireland/SB4Akw5OFmI/AAAAAAAAAVI/gEnBMtAyPbg/s1600-h/adaptiveAggregatedPlanet%5B2%5D.jpg"&gt;&lt;img height="180" alt="adaptiveAggregatedPlanet" src="http://lh6.ggpht.com/john.leonard.ireland/SB4ArQ5OFnI/AAAAAAAAAVQ/RTjB6Ayfpdg/adaptiveAggregatedPlanet_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;In the first image on the left I'm showing (with holes) the old way, a really low detail quad tree, and each quad patch draws a fan. With the new way shown in the image on the right, the quad tree has the same number of levels as in the previous image but each quad patch draws a 17 x 17 grid. The result is that the planet has a much higher level of detail, but the quad tree doesn't.&lt;/p&gt; &lt;p&gt;The trade-off is that the polys aren't culled as accurately as before but that's nothing compared to the gain in FPS (back up to 60 again) for reasonable detail. I'll need to fix holes, cracks and level of detail calculations next, all old news...&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-6833275478137436184?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/6833275478137436184/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=6833275478137436184' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/6833275478137436184'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/6833275478137436184'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/05/planets-04-geomipmapping.html' title='Planets 0.4 - Geomipmapping'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh6.ggpht.com/john.leonard.ireland/SB3_7g5OFjI/AAAAAAAAAUw/tvisMucfsTQ/s72-c/gmmQuadPlanetLevel8_thumb%5B1%5D.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-7663252944984940695</id><published>2008-04-25T16:16:00.001+01:00</published><updated>2008-04-27T13:22:12.846+01:00</updated><title type='text'>Planet Optimisation... Vertex and Index Buffers</title><content type='html'>&lt;p&gt;Not a very interesting post I'm afraid, all I did was optimise a bit (mainly moving all the vertices to a vertex buffer and creating one index buffer for each cube face). Now I can render the planet at a level of detail of 8 (about 750,000 polys) at a reasonable FPS of 50 - before at level 7 (about 200,000 polys) I was only getting 1 FPS!&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SBH1vw5OFdI/AAAAAAAAAUA/QITEvkP7k-U/s1600-h/planetLevel8%5B2%5D.jpg"&gt;&lt;img height="180" alt="planetLevel8" src="http://lh3.ggpht.com/john.leonard.ireland/SBH1ww5OFeI/AAAAAAAAAUI/4kxkI0NCVEs/planetLevel8_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SBH1zQ5OFfI/AAAAAAAAAUQ/lWZm8OKnxC4/s1600-h/PlanetSeam%5B2%5D.jpg"&gt;&lt;img height="180" alt="PlanetSeam" src="http://lh3.ggpht.com/john.leonard.ireland/SBH10w5OFgI/AAAAAAAAAUY/dVm9m5S8Cuw/PlanetSeam_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;I still have a seam problem where the 2 cube faces meet (it's most visible in the bottom right of the second image above) and I think it has to do with the fact that the base textures I have don't wrap in every direction.&lt;/p&gt; &lt;p&gt;I'm not looking forward to implementing CLOD on this sort of sized terrain. I've had issues with Quadtree before where it just took up a load of memory and slowed everything down. I need a good way of aggregating the vertices in the patches I render - and I'm at a loss. Also, I need to be able to dispose of patches I don't use without effecting FPS - I tried this before but with little success.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-7663252944984940695?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/7663252944984940695/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=7663252944984940695' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/7663252944984940695'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/7663252944984940695'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/04/planet-optimisation-vertex-and-index.html' title='Planet Optimisation... Vertex and Index Buffers'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh3.ggpht.com/john.leonard.ireland/SBH1ww5OFeI/AAAAAAAAAUI/4kxkI0NCVEs/s72-c/planetLevel8_thumb.jpg?imgmax=800' height='72' width='72'/><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-750338702927873073</id><published>2008-04-24T13:56:00.001+01:00</published><updated>2008-04-27T13:34:41.583+01:00</updated><title type='text'>Planets 0.3 - Texture</title><content type='html'>&lt;p&gt;I'm not sure why I didn't think of it before, but texturing the planet isn't difficult, each face of the original cube is square so I can just apply the same texturing technique as I did before. I just have to recursively get all the noise values to a certain level of detail, normalise it and use this as a height map. The first go at this wasn't so successful. &lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh4.ggpht.com/john.leonard.ireland/SBCCsQ5OFRI/AAAAAAAAASc/Kh8fUVWBH74/s1600-h/planetTextureBad2%5B3%5D.jpg"&gt;&lt;img height="318" alt="planetTextureBad2" src="http://lh4.ggpht.com/john.leonard.ireland/SBCCwQ5OFSI/AAAAAAAAASk/DsskCw7vrJc/planetTextureBad2_thumb%5B1%5D.jpg?imgmax=800" width="420"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;I used parameters that would create a more asteroid-y looking planetoid just because it's easier to see where the problems are. In the above image I had set a texture coordinate wrong and this recursively led to the whole image looking really scrambled. After I got the coordinates sorted, the next problem appeared:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SBCC1A5OFTI/AAAAAAAAASs/EUf5jDPo_ZE/s1600-h/AsteroidTextureNormalisationProblem%5B3%5D.jpg"&gt;&lt;img height="315" alt="AsteroidTextureNormalisationProblem" src="http://lh4.ggpht.com/john.leonard.ireland/SBCC3Q5OFUI/AAAAAAAAAS0/78MnwS0f0LM/AsteroidTextureNormalisationProblem_thumb%5B1%5D.jpg?imgmax=800" width="420"&gt;&lt;/a&gt;&lt;/p&gt; &lt;p&gt;Basically, because I generate a height map and a texture for each patch (cube face) independently, what might have been the highest height for one patch, isn't the highest for another. So although one patch shows snow for its highest point, the neighbouring patch has higher points than that so it won't use snow for a point of the same height. I probably made that even more confusing than it actually is. Anyways, all I had to do was normalise all the patches with respect to all the other patches. The texture is starting to look like it's covering the model well - but there's a little seam to stretch over...&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SBCC8w5OFVI/AAAAAAAAAS8/Oyg2nnR12ZM/s1600-h/AsteroidSeams%5B6%5D.jpg"&gt;&lt;img height="315" alt="AsteroidSeams" src="http://lh4.ggpht.com/john.leonard.ireland/SBCDCQ5OFWI/AAAAAAAAATE/t1T7T3jaPRM/AsteroidSeams_thumb%5B2%5D.jpg?imgmax=800" width="420"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;Now I've a textured planet! Unfortunately, I think the texture looks far too homogenous (looking the same all over) for an Earth-like planet.&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh4.ggpht.com/john.leonard.ireland/SBCDKQ5OFXI/AAAAAAAAATM/ufCZ0zJFeuk/s1600-h/homogenous%5B2%5D.jpg"&gt;&lt;img height="180" alt="homogenous" src="http://lh3.ggpht.com/john.leonard.ireland/SBCDPA5OFYI/AAAAAAAAATU/FeBzMv-2GIA/homogenous_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SBCDYA5OFZI/AAAAAAAAATc/1o8rMjBkWvI/s1600-h/planetTextured%5B2%5D.jpg"&gt;&lt;img height="180" alt="planetTextured" src="http://lh6.ggpht.com/john.leonard.ireland/SBCDaw5OFaI/AAAAAAAAATk/dZ-tcg9R4vs/planetTextured_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;However they seem like pretty good parameters for a moon or something like that, I just changed a few of the textures and got this moon.&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SBCDgw5OFbI/AAAAAAAAATs/-BfForkNRso/s1600-h/moon%5B3%5D.jpg"&gt;&lt;img height="315" alt="moon" src="http://lh5.ggpht.com/john.leonard.ireland/SBCDjg5OFcI/AAAAAAAAAT0/ouNabwYrMEE/moon_thumb%5B1%5D.jpg?imgmax=800" width="420"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;Oh no... why did I do a full moon??? Now I've got hair growing on the backs of my hands and.... oh no... not now... I've turned into Michael J Fox in Teen Wolf!!! AWOOOOOOOOOOOOOOOOOOOOOOOOOOO!!!!!!!!!!!!!!&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-750338702927873073?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/750338702927873073/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=750338702927873073' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/750338702927873073'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/750338702927873073'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/04/planets-03-texture.html' title='Planets 0.3 - Texture'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh4.ggpht.com/john.leonard.ireland/SBCCwQ5OFSI/AAAAAAAAASk/DsskCw7vrJc/s72-c/planetTextureBad2_thumb%5B1%5D.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-6861871899663791264</id><published>2008-04-23T14:21:00.001+01:00</published><updated>2008-04-23T14:21:04.329+01:00</updated><title type='text'>Planets 0.2 - 3D Noise</title><content type='html'>&lt;p&gt;Geekily enough I have to say adding 3D Perlin Noise to the planet was a lot of fun - it really wasn't a lot of work to move the 2D Perlin Noise code to 3D and I quickly got some visual results. It's frustrating sometimes working with graphics to toil away and have no big change to show for it. The same goes for any programming really, fixing some memory problem can often be a lot more work than creating something visual but the visual change is an obvious and immediate reward. Here's my first application of 3D noise to the procedural sphere:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh4.ggpht.com/john.leonard.ireland/SA8zdg5OFBI/AAAAAAAAAQc/27ZE0q-80V8/s1600-h/3dNoiseWhoops%5B3%5D.jpg"&gt;&lt;img height="298" alt="3dNoiseWhoops" src="http://lh5.ggpht.com/john.leonard.ireland/SA8zfw5OFCI/AAAAAAAAAQk/9SdaLf40-co/3dNoiseWhoops_thumb%5B1%5D.jpg?imgmax=800" width="393"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;Not bad eh? It turns out a lot of geography/astronomy books have totally the wrong idea on how planets look, and it took a lot of origami to make the books mimic what my code produced. Then I thought of having to do all those folds to all those already published books to conform to my model, and I caved to making my model a little more like what the books say. Here are a few different levels of detail for the planetoid - you can see that the noise is always coherent at different levels of detail and doesn't change too much from the previous/next levels.&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SA8zmA5OFDI/AAAAAAAAAQs/-AOSzb1fDks/s1600-h/3dNoiseAsteroid2%5B9%5D.jpg"&gt;&lt;img height="120" alt="3dNoiseAsteroid2" src="http://lh3.ggpht.com/john.leonard.ireland/SA8znQ5OFEI/AAAAAAAAAQ0/5J9tWDf3xLI/3dNoiseAsteroid2_thumb%5B7%5D.jpg?imgmax=800" width="150"&gt;&lt;/a&gt; &lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SA8zvw5OFFI/AAAAAAAAAQ8/Yg4v97J6sFY/s1600-h/3dNoiseAsteroid4%5B9%5D.jpg"&gt;&lt;img height="118" alt="3dNoiseAsteroid4" src="http://lh5.ggpht.com/john.leonard.ireland/SA8zww5OFGI/AAAAAAAAARE/HP4nGz6Nyfw/3dNoiseAsteroid4_thumb%5B7%5D.jpg?imgmax=800" width="150"&gt;&lt;/a&gt; &lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SA8z5A5OFHI/AAAAAAAAARM/2oK-xJ3gzSw/s1600-h/3dNoiseAsteroid6%5B8%5D.jpg"&gt;&lt;img height="117" alt="3dNoiseAsteroid6" src="http://lh6.ggpht.com/john.leonard.ireland/SA8z6A5OFII/AAAAAAAAARU/S-f63WCfwwM/3dNoiseAsteroid6_thumb%5B6%5D.jpg?imgmax=800" width="150"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;Here are a few attempts at a less-asteroidy-more-planety model. The main changes were increasing the frequency parameter of the Perlin Noise and decreasing the height change that the noise would realise. The last one looks most realistic, but on a proper planet, you could barely see the mountains at a distance because the height-scale is so negligent compared to the scale of the planet.&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SA83RQ5OFJI/AAAAAAAAARc/sV84AFsopW8/s1600-h/3dNoiseLumpy%5B3%5D.jpg"&gt;&lt;img height="112" alt="3dNoiseLumpy" src="http://lh6.ggpht.com/john.leonard.ireland/SA83TA5OFKI/AAAAAAAAARk/7k5YS211fAg/3dNoiseLumpy_thumb%5B1%5D.jpg?imgmax=800" width="150"&gt;&lt;/a&gt; &lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SA83ew5OFLI/AAAAAAAAARs/Oc1-RNvbVYw/s1600-h/3dNoiseSpikey%5B3%5D.jpg"&gt;&lt;img height="112" alt="3dNoiseSpikey" src="http://lh6.ggpht.com/john.leonard.ireland/SA83gA5OFMI/AAAAAAAAAR0/4BGxth6kpdo/3dNoiseSpikey_thumb%5B1%5D.jpg?imgmax=800" width="150"&gt;&lt;/a&gt; &lt;a href="http://lh4.ggpht.com/john.leonard.ireland/SA83pg5OFNI/AAAAAAAAAR8/0f6qqQim9_Q/s1600-h/3dNoiseOk%5B3%5D.jpg"&gt;&lt;img height="112" alt="3dNoiseOk" src="http://lh3.ggpht.com/john.leonard.ireland/SA83rQ5OFOI/AAAAAAAAASE/BS9D_m535vM/3dNoiseOk_thumb%5B1%5D.jpg?imgmax=800" width="150"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;Here's a higher level of detail on the surface of the last planet, next I'll need to texture that landscape...&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SA83tw5OFPI/AAAAAAAAASM/kAPfYMBILL8/s1600-h/3dNoiseLandscape%5B3%5D.jpg"&gt;&lt;img height="277" alt="3dNoiseLandscape" src="http://lh3.ggpht.com/john.leonard.ireland/SA83vQ5OFQI/AAAAAAAAASU/UcvLt6b1D4M/3dNoiseLandscape_thumb%5B1%5D.jpg?imgmax=800" width="366"&gt;&lt;/a&gt;&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-6861871899663791264?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/6861871899663791264/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=6861871899663791264' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/6861871899663791264'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/6861871899663791264'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/04/planets-02-3d-noise.html' title='Planets 0.2 - 3D Noise'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh5.ggpht.com/john.leonard.ireland/SA8zfw5OFCI/AAAAAAAAAQk/9SdaLf40-co/s72-c/3dNoiseWhoops_thumb%5B1%5D.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-8118670176502843964</id><published>2008-04-22T22:47:00.001+01:00</published><updated>2008-04-22T22:47:05.737+01:00</updated><title type='text'>Planets 0.1</title><content type='html'>&lt;p&gt;It was really simple to get a little procedural sphere going from a cube, just keep subdividing each face into 4 smaller faces. After thinking about it, I don't think I needed to do anything special to create a planet model because if I texture it with 3 dimensional Perlin noise even a sphere model with a lot of pinching would be fine - anyways, texturing a sphere is for another day. Here are some of my results, FPS doesn't seem to get affected until I get to a level of detail of 5 and then it all goes pear-shaped fast.... well egg-shaped as you'll see...&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SA5cqA5OE4I/AAAAAAAAAPU/xFMudHXTxI8/s1600-h/planet5%5B2%5D.jpg"&gt;&lt;img height="180" alt="planet0" src="http://lh4.ggpht.com/john.leonard.ireland/SA5crw5OE5I/AAAAAAAAAPc/LiBRuyVefrg/planet0_thumb.jpg?imgmax=800" width="240"&gt;&lt;img height="180" alt="planet1" src="http://lh4.ggpht.com/john.leonard.ireland/SA5csw5OE6I/AAAAAAAAAPk/PRvtlvOWWqQ/planet1_thumb.jpg?imgmax=800" width="240"&gt; &lt;img height="180" alt="planet2" src="http://lh5.ggpht.com/john.leonard.ireland/SA5cuA5OE7I/AAAAAAAAAPs/g7uYxKBomcM/planet2_thumb.jpg?imgmax=800" width="240"&gt; &lt;img height="180" alt="planet3" src="http://lh3.ggpht.com/john.leonard.ireland/SA5cvg5OE8I/AAAAAAAAAP0/c3vHrGOL4uA/planet3_thumb.jpg?imgmax=800" width="240"&gt; &lt;img height="180" alt="planet4" src="http://lh4.ggpht.com/john.leonard.ireland/SA5cww5OE9I/AAAAAAAAAP8/cxqXKLu5hkU/planet4_thumb.jpg?imgmax=800" width="240"&gt; &lt;img height="180" alt="planet5" src="http://lh5.ggpht.com/john.leonard.ireland/SA5cyA5OE-I/AAAAAAAAAQE/ET192sGTOTM/planet5_thumb.jpg?imgmax=800" width="240"&gt; &lt;/a&gt;&lt;/p&gt; &lt;p&gt;All bar the last run at 60 FPS (I have vsync on so we can safely assume that the actual FPS is more like 60,000,000 FPS). The last one runs about 30 FPS but this is all pure software, I haven't done anything yet to optimise. Level 6 runs about 7 FPS and level 7... What happened to level 7???&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SA5c0A5OE_I/AAAAAAAAAQM/YHWYk7XQjoE/s1600-h/planet7egg%5B4%5D.jpg"&gt;&lt;img height="381" alt="planet7egg" src="http://lh5.ggpht.com/john.leonard.ireland/SA5c2A5OFAI/AAAAAAAAAQU/nUX5BPPr5QU/planet7egg_thumb%5B2%5D.jpg?imgmax=800" width="500"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;In my sheer brilliant-ness I must have implemented astrophysics while I wasn't really concentrating, this mass of matter is obviously collapsing on itself and probably would implode... and if it ran faster than 1 FPS I'm sure it would look fecking awesome, but I didn't stick around to find out.&lt;/p&gt; &lt;p&gt;So after optimising the sphere stuff a bit, next I'll try to create some textures with Perlin Noise. I get how it works, I'm just a little confused as to how to implement it efficiently. For 2D textures, I have an image that's stretched over the terrain and I give texture coordinates to each point so DirectX does the rest. I can visualise how a 3D Perlin Noise texture looks (like a solid cloud, any slice will create coherent texture and so would a sphere carved out of that material) - but I've no idea how to tell DX about it. I may have to go with colouring each vertex, and then stretching a detail map over it all, but that seems to me like it would look like all kinds of shittyness unless I go to a level of detail so high my planet turns into an egg.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-8118670176502843964?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/8118670176502843964/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=8118670176502843964' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/8118670176502843964'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/8118670176502843964'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/04/planets-01.html' title='Planets 0.1'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh4.ggpht.com/john.leonard.ireland/SA5crw5OE5I/AAAAAAAAAPc/LiBRuyVefrg/s72-c/planet0_thumb.jpg?imgmax=800' height='72' width='72'/><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-7268634898529174087</id><published>2008-04-17T12:24:00.001+01:00</published><updated>2008-04-17T12:24:16.286+01:00</updated><title type='text'>Perlin Noise And Fractals</title><content type='html'>&lt;p&gt;I read up on &lt;a href="http://mrl.nyu.edu/~perlin/"&gt;Ken Perlin&lt;/a&gt; and wanted to try do some terrain using &lt;a href="http://www.gamasutra.com/features/20010302/oneil_01.htm"&gt;Fractal Brownian Motion&lt;/a&gt;. Ken's homepage has tons of little Java applications that each do something innovative with noise - it's good to play about with. Ken came up with a fast way of creating noise and used it to create &lt;a href="http://mrl.nyu.edu/~perlin/doc/hypertexture/"&gt;natural looking textures&lt;/a&gt;. He even won an &lt;a href="http://mrl.nyu.edu/~perlin/doc/oscar.html"&gt;Oscar&lt;/a&gt; for this technique! I had a look at his &lt;a href="http://mrl.nyu.edu/~perlin/doc/oscar.html#noise"&gt;code&lt;/a&gt; and to be honest it was very difficult to follow, sort of like it had been obfuscated. So I looked elsewhere for info but found a lot of people did a sort of hack on Perlin Noise - basically fill an array with random noise and smooth each pixel using the values of neighbouring pixels. I tried this technique out and I wasn't that impressed with the results. It doesn't look too bad but when on an actual terrain, I think it looks too artificial - like the mountains have a grid-like pattern (I tried to highlight this in red on the terrain).&lt;/p&gt; &lt;p align="center"&gt;&amp;nbsp;&lt;a href="http://lh4.ggpht.com/john.leonard.ireland/SAczPmZCU3I/AAAAAAAAANk/Uro_FCAhl14/s1600-h/PerlinHeightMap%5B4%5D.png"&gt;&lt;img height="204" alt="PerlinHeightMap" src="http://lh6.ggpht.com/john.leonard.ireland/SAczQGZCU4I/AAAAAAAAANs/v9LCzXwtQJM/PerlinHeightMap_thumb%5B4%5D.png?imgmax=800" width="204"&gt;&lt;/a&gt; &lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SAczRGZCU5I/AAAAAAAAAN0/PVy1Uaqhcww/s1600-h/perlinhack%5B4%5D.jpg"&gt;&lt;img height="204" alt="perlinhack" src="http://lh4.ggpht.com/john.leonard.ireland/SAczRmZCU6I/AAAAAAAAAN8/rBCh3ySkYX4/perlinhack_thumb%5B2%5D.jpg?imgmax=800" width="267"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;So with the proper Perlin Noise/Fractal Brownian Motion implementation, I think the results are a lot better. To start I wrote a little app so I could quickly try out different combinations of the parameters, here's a screen of it, and some of the results:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SAczSGZCU7I/AAAAAAAAAOE/vJJX-a2nJ0c/s1600-h/perlinnoiseapp%5B4%5D.jpg"&gt;&lt;img height="281" alt="perlinnoiseapp" src="http://lh4.ggpht.com/john.leonard.ireland/SAczSmZCU8I/AAAAAAAAAOM/28dOZOe8dVk/perlinnoiseapp_thumb%5B2%5D.jpg?imgmax=800" width="480"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SAczTGZCU9I/AAAAAAAAAOU/4PjIOx1SEWw/s1600-h/O_7F_0.015A_1L_2P_0.4%5B5%5D.png"&gt;&lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SAczUGZCU-I/AAAAAAAAAOc/EiayrhuMW-A/s1600-h/O_7F_0.01A_1L_2P_0.4%5B2%5D.png"&gt;&lt;img height="150" alt="O_7F_0.01A_1L_2P_0.4" src="http://lh4.ggpht.com/john.leonard.ireland/SAczUmZCU_I/AAAAAAAAAOk/EV6-XAe_g9Q/O_7F_0.01A_1L_2P_0.4_thumb%5B2%5D.png?imgmax=800" width="150"&gt;&lt;/a&gt;&lt;img height="150" alt="O_7F_0.015A_1L_2P_0.4" src="http://lh6.ggpht.com/john.leonard.ireland/SAczVGZCVAI/AAAAAAAAAOs/SkEBq9JxDYg/O_7F_0.015A_1L_2P_0.4_thumb%5B5%5D.png?imgmax=800" width="150"&gt;&lt;/a&gt;&amp;nbsp; &lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SAczV2ZCVBI/AAAAAAAAAO0/5rQ6hDOzcBg/s1600-h/O_8F_0.025A_2L_2.4P_0.56%5B3%5D.png"&gt;&lt;img height="150" alt="O_8F_0.025A_2L_2.4P_0.56" src="http://lh3.ggpht.com/john.leonard.ireland/SAczWWZCVCI/AAAAAAAAAO8/_USni3mUAoI/O_8F_0.025A_2L_2.4P_0.56_thumb%5B3%5D.png?imgmax=800" width="150"&gt;&lt;/a&gt;&amp;nbsp; &lt;/p&gt; &lt;p&gt;Here's some terrain built with a Perlin/fBm height-map:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SAczXWZCVDI/AAAAAAAAAPE/k0cYo4JXwDg/s1600-h/perlinterrain%5B5%5D.jpg"&gt;&lt;img height="371" alt="perlinterrain" src="http://lh5.ggpht.com/john.leonard.ireland/SAczX2ZCVEI/AAAAAAAAAPM/WR1nDzQIZKA/perlinterrain_thumb%5B3%5D.jpg?imgmax=800" width="480"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p align="left"&gt;Another cool thing about Perlin/fBm (if you're a geek I suppose) is that it can be applied to three dimensions too, so I should be able to use it for seamless planet height-maps and textures... but haven't worked it out yet. Often when applying a 2d texture to a sphere artifacts appear, like &lt;a href="http://ozviz.wasp.uwa.edu.au/~pbourke/texture_colour/spheremap/"&gt;pinching at the poles&lt;/a&gt;, but Perlin/fBm should be fine - we'll see! &lt;/p&gt; &lt;p align="left"&gt;Next I really need to do some clean up on my code and after that I'll either look at:&lt;/p&gt; &lt;ul&gt; &lt;li&gt; &lt;div align="left"&gt;making a sphere by recursively splitting a cube's face or...&lt;/div&gt;&lt;/li&gt; &lt;li&gt; &lt;div align="left"&gt;generating the grass, snow and rock textures with Perlin noise&lt;/div&gt;&lt;/li&gt;&lt;/ul&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-7268634898529174087?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/7268634898529174087/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=7268634898529174087' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/7268634898529174087'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/7268634898529174087'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/04/perlin-noise-and-fractals.html' title='Perlin Noise And Fractals'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh6.ggpht.com/john.leonard.ireland/SAczQGZCU4I/AAAAAAAAANs/v9LCzXwtQJM/s72-c/PerlinHeightMap_thumb%5B4%5D.png?imgmax=800' height='72' width='72'/><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-6255176239367081305</id><published>2008-04-16T23:08:00.001+01:00</published><updated>2008-04-16T23:08:21.125+01:00</updated><title type='text'>Adaptive Quadtree</title><content type='html'>&lt;p&gt;I tried hard to optimise my code but in the end I just don't think a quadtree is suited to very large terrain. Here are some of the things I tried:&lt;/p&gt; &lt;ul&gt; &lt;li&gt;The quadtree is now adaptive meaning it only creates children if it needs them to render a more detail  &lt;li&gt;I tried to Dispose() of unused resources on the fly but this really slowed down FPS  &lt;li&gt;The quadtree now uses a shared vertex buffer reducing the number of calls to the device (before each patch would have its own vertex buffer and its own index buffer)  &lt;li&gt;I tried using &lt;a href="http://nprof.sourceforge.net"&gt;NProf&lt;/a&gt; to do some performance analysis on my code, but it didn't help me target anything in particular&lt;/li&gt;&lt;/ul&gt; &lt;p&gt;I'm not 100% sure but I think the main problem is the number of objects needed to render a quadtree increases exponentially when the terrain size increases. With CLOD the number of objects is pretty low in comparison. For a terrain length 256, I use 16 CLOD patches but I would need over 20,000 quad patches. It's a shame, I think quad is neater in the same way that binary search trees are neat. Check out some comparison shots of a large (1024 * 1024 vertices) terrain:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SAZ4LGZCUtI/AAAAAAAAAMU/m2LXd7KEIR0/s1600-h/1024QuadWire2.jpg"&gt;&lt;img height="180" alt="1024QuadWire" src="http://lh5.ggpht.com/john.leonard.ireland/SAZ4NGZCUuI/AAAAAAAAAMc/FdLAewECucc/1024QuadWire_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh3.ggpht.com/john.leonard.ireland/SAZ4VmZCUvI/AAAAAAAAAMk/-1IhhX8ys_g/s1600-h/1024CLODWire2.jpg"&gt;&lt;img height="180" alt="1024CLODWire" src="http://lh3.ggpht.com/john.leonard.ireland/SAZ4XmZCUwI/AAAAAAAAAMs/WzWLBFMdDms/1024CLODWire_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SAZ4eWZCUxI/AAAAAAAAAM0/Ge3_o2MsQHs/s1600-h/1024Quad2.jpg"&gt;&lt;img height="180" alt="1024Quad" src="http://lh5.ggpht.com/john.leonard.ireland/SAZ4gGZCUyI/AAAAAAAAAM8/Y9j23Mmz6Vk/1024Quad_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh6.ggpht.com/john.leonard.ireland/SAZ4mWZCUzI/AAAAAAAAANE/Z1ytP53k40E/s1600-h/1024CLOD2.jpg"&gt;&lt;img height="180" alt="1024CLOD" src="http://lh4.ggpht.com/john.leonard.ireland/SAZ4n2ZCU0I/AAAAAAAAANM/uAMokAAxAN8/1024CLOD_thumb.jpg?imgmax=800" width="240"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;They look similar enough but for the quadtree I was getting about 4 FPS and for with CLOD I was getting between 20-30 FPS. I'll stick with CLOD for planets I think.&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh5.ggpht.com/john.leonard.ireland/SAZ4xGZCU1I/AAAAAAAAANU/rq74wfk73C0/s1600-h/1024ClodLandscape3.jpg"&gt;&lt;img height="377" alt="1024ClodLandscape" src="http://lh4.ggpht.com/john.leonard.ireland/SAZ4z2ZCU2I/AAAAAAAAANc/E8nr1uzE8X0/1024ClodLandscape_thumb1.jpg?imgmax=800" width="497"&gt;&lt;/a&gt;&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-6255176239367081305?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/6255176239367081305/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=6255176239367081305' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/6255176239367081305'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/6255176239367081305'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/04/adaptive-quadtree.html' title='Adaptive Quadtree'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh5.ggpht.com/john.leonard.ireland/SAZ4NGZCUuI/AAAAAAAAAMc/FdLAewECucc/s72-c/1024QuadWire_thumb.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-1246723215678668294</id><published>2008-04-10T16:33:00.001+01:00</published><updated>2008-04-10T16:37:32.501+01:00</updated><title type='text'>Quadtree Holes Fixed</title><content type='html'>&lt;p&gt;I got the holes fixed, it really really hurt my brain. You can see the results here compared to CLOD. There's nothing that different really, just the same terrain with no holes in it. The weird thing is that the quadtree renders a LOT less polys but the FPS is lower. Also, if I try to render a large terrain, quadtree crawls. I'll have to do some optimisation on it next.&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh3.ggpht.com/john.leonard.ireland/R_4zKN3E70I/AAAAAAAAALw/AuNl5IGRKgM/quadnoholes%5B2%5D.jpg"&gt;&lt;img height="180" alt="quadnoholes" src="http://lh4.ggpht.com/john.leonard.ireland/R_4zLd3E71I/AAAAAAAAAL4/oh5VQDJuhiw/quadnoholes_thumb.jpg" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh3.ggpht.com/john.leonard.ireland/R_4zNN3E72I/AAAAAAAAAMA/3_Z0ivnT3Is/clodnoholes%5B2%5D.jpg"&gt;&lt;img height="180" alt="clodnoholes" src="http://lh6.ggpht.com/john.leonard.ireland/R_4zO93E73I/AAAAAAAAAMM/mYU2C7-ZuYw/clodnoholes_thumb.jpg" width="240"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;You can't see it in these pictures but sometime I have these intermittent tiny dots of yellow (so a tiny hole way smaller than a poly) on the quadtree and also tiny hairline cracks with both CLOD and the quadtree.&lt;/p&gt; &lt;p&gt;I think part of the problem is that I'm using my base object which allows an object hierarchy of children to be recursively attached. All this hierarchy does is move each attached child if the parent object moves, so for example, if you move your arm but don't move your hand relative to your arm, your hand should still be in a different position. This is neat for some applications but I think perhaps it's adding unnecessary overhead to the terrain: the patches are all statically fixed unlike joints in an arm. There are inevitable tiny floating point errors which with tons of children attached - like with the patches - is probably causing the hairline cracks. The matrix calculations are adding to the CPU cycles and may be why my quadtree appears to run slower than my CLOD while showing less polys.&lt;/p&gt; &lt;p&gt;So, reluctantly I'll have to overhaul some code and do some optimisation. I hate overhauls, there's little or no visual improvement for a lot of work, but as it stands I think it would take my engine longer to create a world scene than it took the world to be created (even in Creationist terms!) ... stupid Creationists.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-1246723215678668294?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/1246723215678668294/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=1246723215678668294' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/1246723215678668294'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/1246723215678668294'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/04/quadtree-holes-fixed.html' title='Quadtree Holes Fixed'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh4.ggpht.com/john.leonard.ireland/R_4zLd3E71I/AAAAAAAAAL4/oh5VQDJuhiw/s72-c/quadnoholes_thumb.jpg' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-5630289842151429984</id><published>2008-04-09T15:36:00.001+01:00</published><updated>2008-04-09T15:36:43.911+01:00</updated><title type='text'>Quad Tree Termites</title><content type='html'>&lt;p&gt;It's taking a lot longer than I thought but the quadtree implementation is finally taking some shape. Real work (stuff that pays money) took over for a bit so that slowed things down a lot - I also had a holiday around Spain and over to Morocco which was good fun. I climbed a couple of mountains there and I must say God/Buddha/Allah/String theory/Ekpyrotic theory did a good job - no cracks, high detail, no obvious texture repeat and good continuous level of detail (although I wasn't moving very fast). I'd like to see it run on my laptop though.&lt;/p&gt; &lt;p&gt;So anyways, here's a comparison of splitting for CLOD vs. Quadtree in wireframe mode, you can see that the Quadtree is much more precise, the camera position causes a circle of split patches:&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh4.google.com/john.leonard.ireland/R_zUatPh9HI/AAAAAAAAALA/8Ol3Hr_3p8k/clodmesh%5B2%5D.jpg"&gt;&lt;img height="180" alt="clodmesh" src="http://lh6.google.com/john.leonard.ireland/R_zUbNPh9II/AAAAAAAAALI/eRcNhI_mDFE/clodmesh_thumb.jpg" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh3.google.com/john.leonard.ireland/R_zUcdPh9JI/AAAAAAAAALQ/GwqwPRFbrVg/quadmesh%5B2%5D.jpg"&gt;&lt;img height="180" alt="quadmesh" src="http://lh6.google.com/john.leonard.ireland/R_zUdNPh9KI/AAAAAAAAALY/xzp1VBcJoTU/quadmesh_thumb.jpg" width="240"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;The number of polygons rendered is much lower than CLOD, mainly because the frustum culling is much more precise due to the recursive nature of the quadtree implementation. However, I'll need to do a good bit of optimisation, despite the lower number of polygons rendered, the overall FPS is suffering because (I think) of all the recursion needed to draw all the low level polygons.&lt;/p&gt; &lt;p&gt;You might also be able to see all the holes around the circle - it's easier to see in this picture:&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh6.google.com/john.leonard.ireland/R_zUeNPh9LI/AAAAAAAAALg/908VynCwBVg/quadholes%5B4%5D.jpg"&gt;&lt;img height="372" alt="quadholes" src="http://lh5.google.com/john.leonard.ireland/R_zUe9Ph9MI/AAAAAAAAALo/0K1tKgsNdoM/quadholes_thumb%5B2%5D.jpg" width="494"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;Yes, yellow is the new black. All that pink was making my eyes sore, yellow works just as well to show up problems I think.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-5630289842151429984?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/5630289842151429984/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=5630289842151429984' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/5630289842151429984'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/5630289842151429984'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/04/quad-tree-termites.html' title='Quad Tree Termites'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-4581333047267327305</id><published>2008-03-29T17:23:00.001Z</published><updated>2008-03-29T17:33:42.244Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='frustum culling'/><title type='text'>Culling - Spot The Difference</title><content type='html'>&lt;p&gt;I've implemented frustum culling on my terrain, patches that are off-camera won't be rendered. I followed Chad Vernon's tutorial &lt;a href="http://www.chadvernon.com/blog/tutorials/managed-directx-2/frustum-culling/"&gt;here&lt;/a&gt;, it was a very good straightforward tutorial (with source in C#). I'd like to have tutorials like his but I think people (like Chad) can explain things a lot better than I can so I'll leave it to the pros. Anyways, with frustum culling if you were on the terrain looking one direction, everything behind you won't be seen so don't render it. Here are the before and after images, see if you can spot the difference:&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh3.google.com/john.leonard.ireland/R-5699Ph9BI/AAAAAAAAAKQ/kZcFfz51TrA/culloff%5B5%5D.jpg"&gt;&lt;img height="370" alt="culloff" src="http://lh3.google.com/john.leonard.ireland/R-56-9Ph9CI/AAAAAAAAAKY/EcH_n_NEn60/culloff_thumb%5B3%5D.jpg" width="491"&gt;&lt;/a&gt; &lt;a href="http://lh5.google.com/john.leonard.ireland/R-57AdPh9DI/AAAAAAAAAKg/5HixxFyhOP4/cullon%5B5%5D.jpg"&gt;&lt;img height="370" alt="cullon" src="http://lh6.google.com/john.leonard.ireland/R-57BtPh9EI/AAAAAAAAAKo/vMcwiww5qns/cullon_thumb%5B3%5D.jpg" width="493"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;Yeah... the difficult part of showing something that's off-screen is that it's off-screen. In the next shot, I've exaggerated the frustum culling, and instead of culling I'm just rendering the patches in wire frame. So you can see the centre patch is shown and the neighbouring ones are culled.&lt;/p&gt; &lt;p&gt;&lt;a href="http://lh6.google.com/john.leonard.ireland/R-57DtPh9FI/AAAAAAAAAKw/TyNqTV2G7-Q/cullwire%5B4%5D.jpg"&gt;&lt;img height="370" alt="cullwire" src="http://lh4.google.com/john.leonard.ireland/R-57FNPh9GI/AAAAAAAAAK4/ztvjUXZkkC0/cullwire_thumb%5B2%5D.jpg" width="493"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p&gt;It's a huge improvement on the number of polys rendered (and this of course increases the FPS) but I'm sure I'll have to do a few more tricks when I get around to rendering planets. Like for example, fill each solar system with a dense dense fog so you can only see 5 metres in front of you.&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-4581333047267327305?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/4581333047267327305/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=4581333047267327305' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/4581333047267327305'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/4581333047267327305'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/03/culling-spot-difference.html' title='Culling - Spot The Difference'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-2641151868597138876</id><published>2008-03-29T10:18:00.001Z</published><updated>2009-12-21T17:01:56.396Z</updated><title type='text'>Popping</title><content type='html'>&lt;p&gt;I tried geo-morphing on the terrain, but it didn't seem to have any effect really, popping was still quite visible - so instead I changed the way I calculate the LOD to be non-linear. All this means that instead of changing LOD at 100, 200, 300, 400 etc., it changes in relation to how far away it is like 200, 400, 800, 1600. Popping isn't noticeable at all now.&lt;/p&gt;  &lt;p align="center"&gt;&lt;/p&gt;  &lt;p&gt;&lt;/p&gt;  &lt;div style="padding-bottom: 0px; margin: 0px auto; padding-left: 0px; width: 425px; padding-right: 0px; display: block; float: none; padding-top: 0px" id="scid:5737277B-5D6D-4f48-ABFC-DD9C333F4C5D:d3ceb391-c3e2-44d2-99f8-378d8b30be66" class="wlWriterEditableSmartContent"&gt;&lt;div id="61a70f1c-9e99-4baa-b459-5bf0cbc8dc34" style="margin: 0px; padding: 0px; display: inline;"&gt;&lt;div&gt;&lt;a href="http://www.youtube.com/watch?v=kxZOPPn1a60" target="_new"&gt;&lt;img src="http://lh6.ggpht.com/_GaS6iHPgjYA/Sy-qApEYrSI/AAAAAAAALeM/7i76WQ6zjPQ/video4c377d6f0679%5B3%5D.jpg?imgmax=800" style="border-style: none" galleryimg="no" onload="var downlevelDiv = document.getElementById('61a70f1c-9e99-4baa-b459-5bf0cbc8dc34'); downlevelDiv.innerHTML = &amp;quot;&amp;lt;div&amp;gt;&amp;lt;object width=\&amp;quot;425\&amp;quot; height=\&amp;quot;355\&amp;quot;&amp;gt;&amp;lt;param name=\&amp;quot;movie\&amp;quot; value=\&amp;quot;http://www.youtube.com/v/kxZOPPn1a60&amp;amp;hl=en\&amp;quot;&amp;gt;&amp;lt;\/param&amp;gt;&amp;lt;embed src=\&amp;quot;http://www.youtube.com/v/kxZOPPn1a60&amp;amp;hl=en\&amp;quot; type=\&amp;quot;application/x-shockwave-flash\&amp;quot; width=\&amp;quot;425\&amp;quot; height=\&amp;quot;355\&amp;quot;&amp;gt;&amp;lt;\/embed&amp;gt;&amp;lt;\/object&amp;gt;&amp;lt;\/div&amp;gt;&amp;quot;;" alt=""&gt;&lt;/a&gt;&lt;/div&gt;&lt;/div&gt;&lt;/div&gt;  &lt;p align="left"&gt;The video is in 4 parts, with a little of the old in-out:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;     &lt;div align="left"&gt;Linear LOD&lt;/div&gt;   &lt;/li&gt;    &lt;li&gt;     &lt;div align="left"&gt;Non-linear LOD&lt;/div&gt;   &lt;/li&gt;    &lt;li&gt;     &lt;div align="left"&gt;Linear LOD line rendering&lt;/div&gt;   &lt;/li&gt;    &lt;li&gt;     &lt;div align="left"&gt;Non-linear line rendering&lt;/div&gt;   &lt;/li&gt; &lt;/ul&gt;  &lt;p align="left"&gt;The change is most visible in the last section, you can see that the LOD only changes when the vertices are about a pixel apart.&amp;#160; The downside is that it's fairly poly intensive if you're rendering a large patch of terrain - so I might have to make a few compromises when it comes to doing planets.&lt;/p&gt;  &lt;p align="left"&gt;It's my first time uploading a video so hopefully the above shows my terrain stuff and not some whiney emo.&lt;/p&gt;  &lt;p align="left"&gt;&lt;font color="#ff0000"&gt;Update&lt;/font&gt;: video quality was awful so now I know how to do it, I’ve uploaded take 2.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-2641151868597138876?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/2641151868597138876/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=2641151868597138876' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/2641151868597138876'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/2641151868597138876'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/03/popping.html' title='Popping'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh6.ggpht.com/_GaS6iHPgjYA/Sy-qApEYrSI/AAAAAAAALeM/7i76WQ6zjPQ/s72-c/video4c377d6f0679%5B3%5D.jpg?imgmax=800' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-3697981688213608035</id><published>2008-03-24T22:14:00.001Z</published><updated>2008-03-24T22:14:06.988Z</updated><title type='text'>Cracks Painted Over</title><content type='html'>&lt;p&gt;I had to redo the algorithm for creating the index buffer for a patch &lt;em&gt;again&lt;/em&gt; but finally the patches don't show cracks anymore. If a neighbouring patch is at a lower level of detail, I draw the edge that borders that patch a little coarser by omitting a vertex. In the image below left, the red circle indicates where a crack occurs. By omitting the vertex from the higher detailed patch, the poly on the right of the left patch and the poly on the left of the right patch - share an edge. The other image shows where this happens on my engine.&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh6.google.com/john.leonard.ireland/R-gnkNPh85I/AAAAAAAAAJQ/4vUOVY7ISAQ/removevertexfixcrack6.jpg"&gt;&lt;img height="190" alt="removevertexfixcrack" src="http://lh6.google.com/john.leonard.ireland/R-gnlNPh86I/AAAAAAAAAJY/qDB5Wrbl-xs/removevertexfixcrack_thumb4.jpg" width="183"&gt;&lt;/a&gt; &lt;a href="http://lh6.google.com/john.leonard.ireland/R-gnmNPh87I/AAAAAAAAAJg/ILqAP5HY6o8/fixedcracks6.jpg"&gt;&lt;img height="189" alt="fixedcracks" src="http://lh4.google.com/john.leonard.ireland/R-gnmtPh88I/AAAAAAAAAJo/JR_NsrmoCg8/fixedcracks_thumb4.jpg" width="202"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p align="left"&gt;The results aren't very stunning, just the terrain with no cracks:&lt;/p&gt; &lt;p align="left"&gt;&lt;a href="http://lh6.google.com/john.leonard.ireland/R-gnoNPh89I/AAAAAAAAAJw/pNcoclAx-yM/clodnocracks2.jpg"&gt;&lt;img height="180" alt="clodnocracks" src="http://lh6.google.com/john.leonard.ireland/R-gnpNPh8-I/AAAAAAAAAJ4/etjZLdqUJm4/clodnocracks_thumb.jpg" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh3.google.com/john.leonard.ireland/R-gnqdPh8_I/AAAAAAAAAKA/lxV1o8V6UnI/clodnocrackstextured2.jpg"&gt;&lt;img height="180" alt="clodnocrackstextured" src="http://lh6.google.com/john.leonard.ireland/R-gnrNPh9AI/AAAAAAAAAKI/ntW8nDGX4S4/clodnocrackstextured_thumb.jpg" width="240"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p align="left"&gt;One bad side effect of this is that recreating the index buffer each time is a big performance hit. I might pre-calculate all the kinds of index buffers (one set for each level of detail - a set has 16 versions for every configuration that deals with every combination of neighbouring level of details) and share them between the patches. I'm not that bothered about performance at the moment though, I'll just rely on whenever quantum computing comes around to speed my engine up.&lt;/p&gt; &lt;p align="left"&gt;When going towards or away from the terrain, it pops a lot as it changes from one level of detail to the next - so I might look into geomorphing to minimise popping. I think I could come up with a better way of calculating the level of detail too (non-linearly). Or... go back to brute force terrain and wait for quantum computing...&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-3697981688213608035?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/3697981688213608035/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=3697981688213608035' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/3697981688213608035'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/3697981688213608035'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/03/cracks-painted-over.html' title='Cracks Painted Over'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-2907032554767425124</id><published>2008-03-23T16:50:00.001Z</published><updated>2008-03-23T16:50:20.201Z</updated><title type='text'>CLOD - Builder's Crack</title><content type='html'>&lt;p&gt; Why put off something off until tomorrow when you can do it the day after that? I finally got around to doing Continuous Level Of Detail (CLOD), it was really frustrating trying to debug and I had a few restarts on the algorithm because it got so messed up (very handy rolling back with &lt;a href="http://tortoisesvn.tigris.org/"&gt;tortoiseSVN&lt;/a&gt;, &lt;a href="http://subversion.tigris.org/"&gt;SVN&lt;/a&gt; (best source control programs I've used) and &lt;a href="http://unfuddle.com/home"&gt;unfuddle&lt;/a&gt;'s free service).&amp;nbsp; Check out some of the mistakes along the way:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh4.google.com/john.leonard.ireland/R-aKJNPh8vI/AAAAAAAAAIA/jBqRsD_uLvs/clodstrip1%5B2%5D.jpg"&gt;&lt;img height="180" alt="clodstrip1" src="http://lh4.google.com/john.leonard.ireland/R-aKKNPh8wI/AAAAAAAAAII/H3ztChUb-X8/clodstrip1_thumb.jpg" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh3.google.com/john.leonard.ireland/R-aKK9Ph8xI/AAAAAAAAAIQ/_LkPKLPpZDM/clodstrip2%5B2%5D.jpg"&gt;&lt;img height="180" alt="clodstrip2" src="http://lh5.google.com/john.leonard.ireland/R-aKLdPh8yI/AAAAAAAAAIY/naYYN2CJJVU/clodstrip2_thumb.jpg" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh3.google.com/john.leonard.ireland/R-aKM9Ph8zI/AAAAAAAAAIg/Q54yEVB2yVU/CLODv3%5B9%5D.jpg"&gt;&lt;img height="380" alt="CLODv3" src="http://lh3.google.com/john.leonard.ireland/R-aKN9Ph80I/AAAAAAAAAIo/vhbZFxPaP1Q/CLODv3_thumb%5B5%5D.jpg" width="494"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p align="left"&gt;Here's what it looked like when I finally got it working. I've exaggerated when the level of detail changes just so the difference in polygons is obvious. Patches that are close to the camera (bottom right) are more detailed (showing more polygons) than patches farther from the camera (top left)... Shouldn't it be called Non-continuous Level Of Detail?&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh5.google.com/john.leonard.ireland/R-aKPdPh81I/AAAAAAAAAIw/17qjTwncbc0/CLODworking%5B3%5D.jpg"&gt;&lt;img height="339" alt="CLODworking" src="http://lh5.google.com/john.leonard.ireland/R-aKQdPh82I/AAAAAAAAAI4/7KxaMkVbchk/CLODworking_thumb%5B1%5D.jpg" width="447"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p align="left"&gt;So why did I choose a pink background?&amp;nbsp; Well if you've been following fashion, you'll know that pink is the new black - this really held me up as I had to write a custom Color class which would swap colours around dependent on current trends. A handy side effect though is that it shows up the cracks that can occur using CLOD like the one on the top right:&lt;/p&gt; &lt;p align="center"&gt;&lt;a href="http://lh3.google.com/john.leonard.ireland/R-aKR9Ph83I/AAAAAAAAAJA/k9Kf7LLAaBA/CLODcracked%5B4%5D.jpg"&gt;&lt;img height="342" alt="CLODcracked" src="http://lh3.google.com/john.leonard.ireland/R-aKS9Ph84I/AAAAAAAAAJI/x5DxHSP52RY/CLODcracked_thumb%5B2%5D.jpg" width="454"&gt;&lt;/a&gt; &lt;/p&gt; &lt;p align="left"&gt;The cracks occur when 2 patches of different detail levels are beside each other, the more detailed patch has a vertex on the patch border where the less detailed patch doesn't. I'll have to increase the level of detail on any edge of a patch that borders a higher detail neighbour in order to *patch* up the cracks - get it??&amp;nbsp; See what I did there???&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-2907032554767425124?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/2907032554767425124/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=2907032554767425124' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/2907032554767425124'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/2907032554767425124'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/03/clod-builder-crack.html' title='CLOD - Builder&amp;#39;s Crack'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-668287841565535779</id><published>2008-03-20T14:48:00.001Z</published><updated>2008-03-29T10:23:16.743Z</updated><title type='text'>Seasons</title><content type='html'>&lt;p&gt;I'm still avoiding CLOD, but the distraction I came up with was kinda cool so I thought I'd share. It occurred to me that I could create a neat seasonal effect if I play with the terrain texturing. Terrain texturing is a single texture made from a blend of base textures, the blend depends on the height of the terrain at a certain point and the height range for each base texture. Well, if we were to multiply each height by a factor when we're working out what texture to use so that the heights appeared to be bigger than usual, then we'd get a lot more snowy texture on the terrain (and vice versa for grass). I had to include a couple of extreme cases in the existing code (like if the height is higher than the max range of the snow texture, just make it snow) but it was simple to add the seasonal factor. Here's what the effect produced:&lt;/p&gt;&lt;p&gt;&lt;a href="http://lh4.google.com/john.leonard.ireland/R-KPANPh8uI/AAAAAAAAAHQ/mT8R0HNMZSY/season1%5B4%5D" target=""&gt;&lt;img height="180" alt="season1" src="http://lh4.google.com/john.leonard.ireland/R-J5ENPh8iI/AAAAAAAAAHU/wBhV-M5jFOc/season1_thumb%5B3%5D" width="240" /&gt;&lt;/a&gt; &lt;a href="http://lh4.google.com/john.leonard.ireland/R-J5GNPh8jI/AAAAAAAAAHY/A_wKeKrV-aQ/season2%5B3%5D" target=""&gt;&lt;img height="180" alt="season2" src="http://lh3.google.com/john.leonard.ireland/R-J5G9Ph8kI/AAAAAAAAAHc/4TTh28RXhX0/season2_thumb%5B2%5D" width="240" /&gt;&lt;/a&gt; &lt;a href="http://lh5.google.com/john.leonard.ireland/R-J5IdPh8lI/AAAAAAAAAHg/IElP7XVucyQ/season3%5B3%5D" target=""&gt;&lt;img height="180" alt="season3" src="http://lh5.google.com/john.leonard.ireland/R-J5JdPh8mI/AAAAAAAAAHk/OGOqOh_4Ekc/season3_thumb%5B2%5D" width="240" /&gt;&lt;/a&gt; &lt;a href="http://lh6.google.com/john.leonard.ireland/R-J5KtPh8nI/AAAAAAAAAHo/nZbtVzYRFGI/season4%5B3%5D" target=""&gt;&lt;img height="180" alt="season4" src="http://lh3.google.com/john.leonard.ireland/R-J5L9Ph8oI/AAAAAAAAAHs/dM4YbfE7njY/season4_thumb%5B2%5D" width="240" /&gt;&lt;/a&gt; &lt;a href="http://lh3.google.com/john.leonard.ireland/R-J5M9Ph8pI/AAAAAAAAAHw/YtBP8BQJhM0/season5%5B3%5D" target=""&gt;&lt;img height="180" alt="season5" src="http://lh3.google.com/john.leonard.ireland/R-J5N9Ph8qI/AAAAAAAAAH0/FuYK2EKbOXM/season5_thumb%5B2%5D" width="240" /&gt;&lt;/a&gt; &lt;a href="http://lh4.google.com/john.leonard.ireland/R-J5PNPh8rI/AAAAAAAAAH4/HiRuDACkab8/season6%5B3%5D" target=""&gt;&lt;img height="180" alt="season6" src="http://lh3.google.com/john.leonard.ireland/R-J5P9Ph8sI/AAAAAAAAAH8/MZfRnL39__g/season6_thumb%5B2%5D" width="240" /&gt;&lt;/a&gt; &lt;/p&gt;&lt;p&gt;It's nice to watch the snow creep in over time, but it really slows the frame rate right down (to about 2 fps). I worked with Bitmaps in C# before and it seems to be about 100 times faster to lock the pixels and access them directly rather than use GetPixel and SetPixel. I'm also sure there are fancy hardware things you could do too.&lt;/p&gt;&lt;br /&gt;&lt;object width="425" height="350"&gt; &lt;param name="movie" value="http://www.youtube.com/v/yzHe4pmm7Vo"&gt; &lt;/param&gt; &lt;embed src="http://www.youtube.com/v/yzHe4pmm7Vo" type="application/x-shockwave-flash" width="425" height="350"&gt; &lt;/embed&gt; &lt;/object&gt;&lt;br /&gt;&lt;p&gt;If I keep up these distractions, the real-world season is likely to change before I get on with CLOD. Well, except here, it seems to be cold and rainy season indefinitely.&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-668287841565535779?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/668287841565535779/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=668287841565535779' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/668287841565535779'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/668287841565535779'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/03/seasons.html' title='Seasons'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-239843779286933516</id><published>2008-03-20T14:13:00.001Z</published><updated>2008-03-20T14:13:22.998Z</updated><title type='text'>Light Mapping</title><content type='html'>&lt;p&gt;Ok, so I'm putting CLOD on hold for a bit, I'm not looking forward to be honest given I've pretty much forgotten everything to do with geometry. So instead I implemented light mapping. Light mapping is just darkening pixels on the terrain so it looks like a light is casting shadows. The simplest and most visually attractive technique in my opinion is slope lighting. Following a line of pixels in a direction from where the light source should be (in this case I chose south (which is x = 0, z = -1)), make the current pixel darker than the previous by a factor of how much higher the previous height is. If the previous pixel is lower than the current pixel, don't darken it.&lt;/p&gt;&lt;pre class="code"&gt;shade = 1.0f - ((heightMap[x - xLightDir, z - zLightDir] - heightMap[x, z]) / softness);&lt;/pre&gt;&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;&lt;br /&gt;&lt;p&gt;As always you can play about with parameters to make the light come from a different direction, or to create a more severe (darker) shadow. Here's how the effect looks in practice on my engine (before and after):&lt;/p&gt;&lt;br /&gt;&lt;p align="center"&gt;&lt;a href="http://lh5.google.com/john.leonard.ireland/R-Jw8dPh8dI/AAAAAAAAADg/A8OBz80D0Pk/nonlightmapped%5B3%5D"&gt;&lt;img height="140" alt="nonlightmapped" src="http://lh4.google.com/john.leonard.ireland/R-Jw9NPh8eI/AAAAAAAAADo/2fWZ2tEcW1o/nonlightmapped_thumb%5B1%5D" width="240"&gt;&lt;/a&gt; &lt;a href="http://lh4.google.com/john.leonard.ireland/R-Jw_NPh8fI/AAAAAAAAADw/4KYj8QY3RFg/lightmapped%5B3%5D"&gt;&lt;img height="140" alt="lightmapped" src="http://lh4.google.com/john.leonard.ireland/R-JxANPh8gI/AAAAAAAAAD4/jhLo2RIM2us/lightmapped_thumb%5B1%5D" width="240"&gt;&lt;/a&gt; &lt;/p&gt;&lt;br /&gt;&lt;p align="left"&gt;It's not proper shadowing but I like the effect. I think it could be extended to stretch the shadows - for example a low sun would create long shadows, so you probably could choose a direction as above with a shadow range of 10 (something like x = 0, z = -10). However sections of the edges would look a bit out of place because they don't have 10 pixels before them.&lt;/p&gt;&lt;br /&gt;&lt;p align="left"&gt;For a realistic Irish effect you don't need shadows at all because there's no direct light source, just make sure to turn the colour of your ambient light to dark grey.&lt;/p&gt;  &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-239843779286933516?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/239843779286933516/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=239843779286933516' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/239843779286933516'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/239843779286933516'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/03/light-mapping.html' title='Light Mapping'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-8984605970479912921</id><published>2008-03-20T08:34:00.001Z</published><updated>2008-03-20T08:53:34.657Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='texturing'/><category scheme='http://www.blogger.com/atom/ns#' term='managed'/><category scheme='http://www.blogger.com/atom/ns#' term='detail map'/><category scheme='http://www.blogger.com/atom/ns#' term='directx'/><title type='text'>Adding Detail Map - Looks Fuzzy</title><content type='html'>&lt;p&gt;To counteract the blurriness of the terrain, I'll apply a detail map.  A detail map is just a plain texture with some details like cracks and bumps. The detail map will be applied 32 times over the terrain, here's what the result looks like (before and after):&lt;/p&gt;&lt;p align="center"&gt;&lt;a href="http://lh3.google.com/john.leonard.ireland/R-IhZ9Ph8VI/AAAAAAAAACg/hHWopJ8zUcU/closenotfuzzy%5B3%5D"&gt;&lt;img height="175" alt="closenotfuzzy" src="http://lh6.google.com/john.leonard.ireland/R-IhatPh8WI/AAAAAAAAACo/t0VoyNieocg/closenotfuzzy_thumb%5B1%5D" width="240" /&gt;&lt;/a&gt; &lt;a href="http://lh4.google.com/john.leonard.ireland/R-IhcNPh8XI/AAAAAAAAACw/4RBhbD3bRKY/closefuzzy%5B3%5D"&gt;&lt;img height="175" alt="closefuzzy" src="http://lh3.google.com/john.leonard.ireland/R-Ihc9Ph8YI/AAAAAAAAAC4/h8lH4Snn8Rk/closefuzzy_thumb%5B1%5D" width="240" /&gt;&lt;/a&gt; &lt;/p&gt;&lt;p&gt;It looks a bit more realistic, but it seems to be really noisy and fuzzy when I fly towards it (that is when I fly using the camera controls, not in real life - I didn't take any crystal meth or anything). Here's what it looks like from far away (before and after):&lt;/p&gt;&lt;p align="center"&gt;&lt;a href="http://lh3.google.com/john.leonard.ireland/R-Ihd9Ph8ZI/AAAAAAAAADA/iXvCNLZYL_A/notfuzzy%5B9%5D"&gt;&lt;img height="287" alt="notfuzzy" src="http://lh3.google.com/john.leonard.ireland/R-Ihe9Ph8aI/AAAAAAAAADI/P0IpxuzWWgc/notfuzzy_thumb%5B7%5D" width="490" /&gt;&lt;/a&gt; &lt;a href="http://lh3.google.com/john.leonard.ireland/R-Ihf9Ph8bI/AAAAAAAAADQ/TOJ0jvykbiw/fuzzy3%5B5%5D"&gt;&lt;img height="286" alt="fuzzy3" src="http://lh3.google.com/john.leonard.ireland/R-Ihg9Ph8cI/AAAAAAAAADY/uJjA3priUgI/fuzzy3_thumb%5B3%5D" width="490" /&gt;&lt;/a&gt; &lt;/p&gt;&lt;p align="left"&gt;It's easiest to see the fuzzy noise on the black pit to the right. It's hard to tell from the images but it's worst when you move toward the terrain; pixels on the detail map seem to move about and make it look something like there's interference on a TV channel. When I release my game I'll just include a superficial aerial with it - problem solved.&lt;/p&gt;&lt;p align="left"&gt;A lot of these sort of problems can be fixed with manipulating some of the parameters (like how many times the detail map is repeated over the terrain). There are already tons of parameters I've arbitrarily picked and I just run the project to see what it looks like, then change them again - which takes up a bit of time. I'm thinking of writing some sort of Reflection-based ParameterManager class so I can easily cycle through all available parameters at run-time and save/load sets. I'll put that on the back-burner though because my terrain performs horribly at the moment so I'll do some optimisation with Continuous Level Of Detail (CLOD) next time.&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-8984605970479912921?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/8984605970479912921/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=8984605970479912921' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/8984605970479912921'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/8984605970479912921'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/03/adding-detail-map-looks-fuzzy.html' title='Adding Detail Map - Looks Fuzzy'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-8956736027918193708</id><published>2008-03-20T00:18:00.001Z</published><updated>2008-03-20T00:20:08.658Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='texturing'/><category scheme='http://www.blogger.com/atom/ns#' term='terrain'/><category scheme='http://www.blogger.com/atom/ns#' term='blending'/><category scheme='http://www.blogger.com/atom/ns#' term='software'/><category scheme='http://www.blogger.com/atom/ns#' term='directx'/><title type='text'>Terrain Texturing</title><content type='html'>&lt;p&gt;After I put in the camera rotation code from my last post, the teeth-like artifacts disappeared. I find graphical programs a real bitch to debug so I'm pretty happy to totally block from memory that they ever existed... what was I talking about? Oh yeah, texturing the terrain.&lt;/p&gt;&lt;p&gt;Instead of colouring the vertex based on how high it is, we'll texture it. With height-colouring it was simple to go from black to white, it's just as easy going from one texture to another - the technique is pretty much the same but the start and end colours are retrieved from a specific point on each texture. Blending is done as before, if the point is nearer the higher texture, the point will be closer in colour to the pixel from the higher texture and vice versa for the lower texture.  Here's the result of applying 4 textures (earth, grass, rock and snow) to my terrain:&lt;/p&gt;&lt;p align="center"&gt;&lt;a href="http://lh4.google.com/john.leonard.ireland/R-GtIdPh8LI/AAAAAAAAABQ/rNy5yVj4u1I/0%5B12%5D"&gt;&lt;img height="70" alt="0" src="http://lh3.google.com/john.leonard.ireland/R-GtJNPh8MI/AAAAAAAAABY/_Xkv5SNi5zc/0_thumb%5B12%5D" width="70" /&gt;&lt;/a&gt; &lt;a href="http://lh6.google.com/john.leonard.ireland/R-GtK9Ph8NI/AAAAAAAAABg/wIZOvhrbvEw/1%5B11%5D"&gt;&lt;img height="70" alt="1" src="http://lh5.google.com/john.leonard.ireland/R-GtLtPh8OI/AAAAAAAAABo/aCrYrQI1s3k/1_thumb%5B11%5D" width="70" /&gt;&lt;/a&gt; &lt;a href="http://lh6.google.com/john.leonard.ireland/R-GtM9Ph8PI/AAAAAAAAABw/R5aI88iSKO4/2%5B2%5D"&gt;&lt;img height="70" alt="2" src="http://lh5.google.com/john.leonard.ireland/R-GtNtPh8QI/AAAAAAAAAB4/IOfEzRxrqxI/2_thumb%5B2%5D" width="70" /&gt;&lt;/a&gt; &lt;a href="http://lh6.google.com/john.leonard.ireland/R-GtO9Ph8RI/AAAAAAAAACA/sfH-0B_JVps/3%5B2%5D"&gt;&lt;img height="70" alt="3" src="http://lh6.google.com/john.leonard.ireland/R-GtP9Ph8SI/AAAAAAAAACI/zgRPXhw0euk/3_thumb%5B2%5D" width="70" /&gt;&lt;/a&gt; &lt;/p&gt;&lt;p align="center"&gt;&lt;a href="http://lh6.google.com/john.leonard.ireland/R-GtQ9Ph8TI/AAAAAAAAACQ/UPOufcs5HPM/texturedterrain%5B4%5D"&gt;&lt;img height="184" alt="texturedterrain" src="http://lh6.google.com/john.leonard.ireland/R-GtR9Ph8UI/AAAAAAAAACY/6Syjqc2180A/texturedterrain_thumb%5B2%5D" width="296" /&gt;&lt;/a&gt; &lt;/p&gt;&lt;p align="left"&gt;It looks more realistic, but a little bit blurry. The pit on the right looks black instead of earthy because I started blending off with a black colour as a base, I think it looks ok.&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-8956736027918193708?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/8956736027918193708/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=8956736027918193708' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/8956736027918193708'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/8956736027918193708'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/03/terrain-texturing.html' title='Terrain Texturing'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-3532892781895664734</id><published>2008-03-19T22:55:00.001Z</published><updated>2008-03-19T23:20:09.678Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='pitch'/><category scheme='http://www.blogger.com/atom/ns#' term='roll'/><category scheme='http://www.blogger.com/atom/ns#' term='rotation'/><category scheme='http://www.blogger.com/atom/ns#' term='managed'/><category scheme='http://www.blogger.com/atom/ns#' term='camera'/><category scheme='http://www.blogger.com/atom/ns#' term='yaw'/><category scheme='http://www.blogger.com/atom/ns#' term='matrix.rotationyawpitchroll'/><category scheme='http://www.blogger.com/atom/ns#' term='directx'/><title type='text'>Proper Camera Rotation</title><content type='html'>&lt;p&gt;In order to have a better look at the weird artefacts on my terrain, I tried to add a mouse &amp;amp;amp; keyboard controlled camera. Matrix.RotationYawPitchRoll doesn't seem to work for me - if I rotate my camera 90 degrees about the Y axis (yaw) looking to my left then try to rotate about the Z axis (roll) so the view spins clockwise it actually rotates around the X axis (pitch) and ends up looking up and down. &lt;p&gt;(I suppose I should've said on the first post that I'm writing the game in Managed DirectX with C#). &lt;p&gt;Anyways, I had this problem before when I was good at geometry so I was sure I could do it again. Unfortunately years of boozing have destroyed any remnants of my secondary school geometry and the results of my sin/cos calculations were that I should go get my old computer out of the shed and get the old code. Here it is if anyone has the same problem: &lt;div  style="color:white;"&gt;&lt;pre class="code"&gt;&lt;span style="color:blue;"&gt;private void &lt;/span&gt;Rotate(&lt;span style="color:blue;"&gt;float &lt;/span&gt;yaw, &lt;span style="color:blue;"&gt;float &lt;/span&gt;pitch, &lt;span style="color:blue;"&gt;float &lt;/span&gt;roll)&lt;br /&gt;{&lt;br /&gt;    &lt;span style="color:green;"&gt;// We'll create 3 matrices for the combined rotation&lt;br /&gt;    &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;Matrix &lt;/span&gt;yawMatrix = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;Matrix &lt;/span&gt;();&lt;br /&gt;    &lt;span style="color:#2b91af;"&gt;Matrix &lt;/span&gt;pitchMatrix = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;Matrix &lt;/span&gt;();&lt;br /&gt;    &lt;span style="color:#2b91af;"&gt;Matrix &lt;/span&gt;rollMatrix = &lt;span style="color:blue;"&gt;new &lt;/span&gt;&lt;span style="color:#2b91af;"&gt;Matrix &lt;/span&gt;();&lt;br /&gt;&lt;br /&gt;    _localMatrix.Translate(_position);&lt;br /&gt;&lt;br /&gt;    &lt;span style="color:green;"&gt;// Reset it's orientation vectors to make sure they're all&lt;br /&gt;    // sqare against each other and unit length&lt;br /&gt;    &lt;/span&gt;_look.Normalize();&lt;br /&gt;    _right = &lt;span style="color:#2b91af;"&gt;Vector3&lt;/span&gt;.Cross(_up, _look);&lt;br /&gt;    _right.Normalize();&lt;br /&gt;    _up = &lt;span style="color:#2b91af;"&gt;Vector3&lt;/span&gt;.Cross(_look, _right);&lt;br /&gt;    _up.Normalize();&lt;br /&gt;&lt;br /&gt;    &lt;span style="color:green;"&gt;// The pitch rotation will be done about the x axis (right)&lt;br /&gt;    &lt;/span&gt;pitchMatrix.RotateAxis(_right, pitch);&lt;br /&gt;    &lt;span style="color:green;"&gt;// The yaw rotation will be done about the y axis (up)&lt;br /&gt;    &lt;/span&gt;yawMatrix.RotateAxis(_up, yaw);&lt;br /&gt;    &lt;span style="color:green;"&gt;// The roll rotation will be done about the z axis (look)&lt;br /&gt;    &lt;/span&gt;rollMatrix.RotateAxis(_look, roll);&lt;br /&gt;&lt;br /&gt;    &lt;span style="color:green;"&gt;// Rotate the local axis about these matrices so we can tell&lt;br /&gt;    // how the object is now oriented after rotation&lt;br /&gt;&lt;br /&gt;    // Rotate the _look and _right about the yaw rotation&lt;br /&gt;    &lt;/span&gt;_look.TransformCoordinate(yawMatrix);&lt;br /&gt;    _right.TransformCoordinate(yawMatrix);&lt;br /&gt;&lt;br /&gt;    &lt;span style="color:green;"&gt;// Rotate the _up and _right about the roll rotation&lt;br /&gt;    &lt;/span&gt;_up.TransformCoordinate(rollMatrix);&lt;br /&gt;    _right.TransformCoordinate(rollMatrix);&lt;br /&gt;&lt;br /&gt;    &lt;span style="color:green;"&gt;// Rotate the _look and _up about the pitch rotation&lt;br /&gt;    &lt;/span&gt;_look.TransformCoordinate(pitchMatrix);&lt;br /&gt;    _up.TransformCoordinate(pitchMatrix);&lt;br /&gt;&lt;br /&gt;    &lt;span style="color:green;"&gt;// Store this in the local matrix for translation when rendering&lt;br /&gt;    &lt;/span&gt;_localMatrix.M11 = _right.X;&lt;br /&gt;    _localMatrix.M12 = _right.Y;&lt;br /&gt;    _localMatrix.M13 = _right.Z;&lt;br /&gt;&lt;br /&gt;    _localMatrix.M21 = _up.X;&lt;br /&gt;    _localMatrix.M22 = _up.Y;&lt;br /&gt;    _localMatrix.M23 = _up.Z;&lt;br /&gt;&lt;br /&gt;    _localMatrix.M31 = _look.X;&lt;br /&gt;    _localMatrix.M32 = _look.Y;&lt;br /&gt;    _localMatrix.M33 = _look.Z;&lt;br /&gt;}&lt;/pre&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-3532892781895664734?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/3532892781895664734/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=3532892781895664734' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/3532892781895664734'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/3532892781895664734'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/03/proper-camera-rotation.html' title='Proper Camera Rotation'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8902496644393737364.post-8626342387990700509</id><published>2008-03-19T20:38:00.000Z</published><updated>2008-03-19T23:20:55.014Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='terrain'/><category scheme='http://www.blogger.com/atom/ns#' term='fault formation'/><category scheme='http://www.blogger.com/atom/ns#' term='3d'/><category scheme='http://www.blogger.com/atom/ns#' term='engine'/><category scheme='http://www.blogger.com/atom/ns#' term='nibbles'/><category scheme='http://www.blogger.com/atom/ns#' term='game'/><category scheme='http://www.blogger.com/atom/ns#' term='directx'/><title type='text'>First post!!!!!</title><content type='html'>Hello! I'm writing this blog for purely selfish reasons - I've wanted to program games since I was a kid but have only once finished a project: a Nibbles clone with death sequences in DOS (I'll put up the exe if anyone's interested). A friend suggested that a blog can help so hopefully some sort of guilt for updating this blog will override my incredible laziness. He's got a game engine in development too and has made a lot of progress, it looks fantastic and you can see it on his &lt;a href="http://decadeengine.blogspot.com/"&gt;blog &lt;/a&gt;- feel free to make me feel better and undermine him and his engine :)&lt;br /&gt;&lt;br /&gt;So what'll my game be then? I don't know yet, but my ambitions are high - basically I'd like a procedurally created universe with super-intelligent AI with a combined RPG/FPS/Flight/Driving/Adventure gameplay that's fecking awesome. People will become addicted to my game and it will create world peace. Oh and I'll get the ride off of some hot groupies. But I've got to start somewhere, so here we go - a terrain (bit of land) generated with fault formation (raise sections of the land randomly) and lit with height lighting (the higher the whiter). These are real terrain basics so I won't go into detail (unless someone needs it).&lt;br /&gt;&lt;br /&gt;&lt;img id="BLOGGER_PHOTO_ID_5179568753932890242" style="DISPLAY: block; MARGIN: 0px auto 10px; CURSOR: hand; TEXT-ALIGN: center" alt="" src="http://3.bp.blogspot.com/_GaS6iHPgjYA/R-GGVtPh8II/AAAAAAAAAAM/cVg9G40trgI/s320/heightcolouredterrain.jpg" border="0" /&gt;&lt;br /&gt;Looks ok for a first go, but there are these weird artefacts, kinda like teeth, no idea what they are... &lt;img id="BLOGGER_PHOTO_ID_5179569565681709202" style="DISPLAY: block; MARGIN: 0px auto 10px; CURSOR: hand; TEXT-ALIGN: center" alt="" src="http://4.bp.blogspot.com/_GaS6iHPgjYA/R-GHE9Ph8JI/AAAAAAAAAAU/YTQQsFSB9m4/s320/artefact.jpg" border="0" /&gt;&lt;br /&gt;Until next time!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8902496644393737364-8626342387990700509?l=jellyengine.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jellyengine.blogspot.com/feeds/8626342387990700509/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8902496644393737364&amp;postID=8626342387990700509' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/8626342387990700509'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8902496644393737364/posts/default/8626342387990700509'/><link rel='alternate' type='text/html' href='http://jellyengine.blogspot.com/2008/03/first-post.html' title='First post!!!!!'/><author><name>John Leonard</name><uri>http://www.blogger.com/profile/00406177658806561437</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://3.bp.blogspot.com/_GaS6iHPgjYA/R-GGVtPh8II/AAAAAAAAAAM/cVg9G40trgI/s72-c/heightcolouredterrain.jpg' height='72' width='72'/><thr:total>0</thr:total></entry></feed>
