<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0" xmlns:itunes="http://www.itunes.com/dtds/podcast-1.0.dtd" xmlns:googleplay="http://www.google.com/schemas/play-podcasts/1.0"><channel><title><![CDATA[Mohammad [808gg] Ashour]]></title><description><![CDATA[Love and work. Creating video games and digital sauces with awesome people. Writing about whatever the week/month brings up.]]></description><link>https://www.808gg.xyz</link><image><url>https://www.808gg.xyz/img/substack.png</url><title>Mohammad [808gg] Ashour</title><link>https://www.808gg.xyz</link></image><generator>Substack</generator><lastBuildDate>Sun, 19 Apr 2026 01:19:12 GMT</lastBuildDate><atom:link href="https://www.808gg.xyz/feed" rel="self" type="application/rss+xml"/><copyright><![CDATA[Mohammad Ashour]]></copyright><language><![CDATA[en]]></language><webMaster><![CDATA[808gg@substack.com]]></webMaster><itunes:owner><itunes:email><![CDATA[808gg@substack.com]]></itunes:email><itunes:name><![CDATA[Mohammad [808gg] Ashour]]></itunes:name></itunes:owner><itunes:author><![CDATA[Mohammad [808gg] Ashour]]></itunes:author><googleplay:owner><![CDATA[808gg@substack.com]]></googleplay:owner><googleplay:email><![CDATA[808gg@substack.com]]></googleplay:email><googleplay:author><![CDATA[Mohammad [808gg] Ashour]]></googleplay:author><itunes:block><![CDATA[Yes]]></itunes:block><item><title><![CDATA[Abnormally Baking Normals]]></title><description><![CDATA[On beginner's mind, AI hallucinations, and learning Blender (also a tutorial, I guess)]]></description><link>https://www.808gg.xyz/p/abnormally-baking-normals</link><guid isPermaLink="false">https://www.808gg.xyz/p/abnormally-baking-normals</guid><dc:creator><![CDATA[Mohammad [808gg] Ashour]]></dc:creator><pubDate>Fri, 18 Jul 2025 22:34:24 GMT</pubDate><enclosure url="https://substackcdn.com/image/fetch/$s_!9dwM!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4678c086-a847-47fa-a48e-d4c4b37be9e0_1558x1247.jpeg" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>I&#8217;m learning the Blender 3D modelling program as part of my current work transition from full-stack web developer to 3D web developer (with half-full stacks?)</em></p><div><hr></div><p>Yesterday, I went into Blender to bake some normals: converting the details of a 3D model to a 2D image placed atop a lower detail (low-poly) version of the same model. This baked <em>normal map</em> is used to interact with lights in the scene, effectively detailing a low-poly model without the computational cost of excess geometry. </p><p>The Blender baking learning curve was painful. Not a nightmare, but one of those &#8220;what have I gotten myself into?&#8221; moments. The process seemed easy enough on paper. In practice, I was jumping between different panels and modes all the time, and it was all a bit bewildering to a beginner like me.</p><h2>The Trumpian confidence of ChadGPT</h2><p>I used my go-to rubber-duck/search-engine-replacement, ChatGPT, to walk me through the Blender bake steps. It was largely OK and came up with a pretty good step-by-step tutorial. With one hiccup.</p><p>At one point, the LLM was <em>very confident</em> that you could bake normals from a high-poly to a low-poly model, even if the models are far apart. This is horse doodoo. To bake normals, Blender casts rays from the low-poly model towards the high-poly model, so the models must be on top of each other. ChatGPT&#8217;s very confident hallucination cost me a significant amount of time. It also, and not for the first time, shook my confidence in the reliability of LLMs.</p><p>A good old-fashioned <a href="https://youtu.be/j3lwBDtC0ic?si=ZQvaQqlVNGmqmRvV">33-second human-made video tutorial</a> helped me resolve the issue, and I finally got my normals baked properly. And, to be fair, ChatGPT did guide me through most of the process. It just pooped itself that one time and was so confident that no pooping occurred that I started questioning my intuition.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="https://substackcdn.com/image/fetch/$s_!9dwM!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4678c086-a847-47fa-a48e-d4c4b37be9e0_1558x1247.jpeg" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!9dwM!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4678c086-a847-47fa-a48e-d4c4b37be9e0_1558x1247.jpeg 424w, https://substackcdn.com/image/fetch/$s_!9dwM!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4678c086-a847-47fa-a48e-d4c4b37be9e0_1558x1247.jpeg 848w, https://substackcdn.com/image/fetch/$s_!9dwM!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4678c086-a847-47fa-a48e-d4c4b37be9e0_1558x1247.jpeg 1272w, https://substackcdn.com/image/fetch/$s_!9dwM!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4678c086-a847-47fa-a48e-d4c4b37be9e0_1558x1247.jpeg 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!9dwM!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4678c086-a847-47fa-a48e-d4c4b37be9e0_1558x1247.jpeg" width="1456" height="1165" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/4678c086-a847-47fa-a48e-d4c4b37be9e0_1558x1247.jpeg&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:1165,&quot;width&quot;:1456,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;https://cdn.mos.cms.futurecdn.net/9W4PYwVd9sQTT9NmJfK9TQ.jpg&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="https://cdn.mos.cms.futurecdn.net/9W4PYwVd9sQTT9NmJfK9TQ.jpg" title="https://cdn.mos.cms.futurecdn.net/9W4PYwVd9sQTT9NmJfK9TQ.jpg" srcset="https://substackcdn.com/image/fetch/$s_!9dwM!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4678c086-a847-47fa-a48e-d4c4b37be9e0_1558x1247.jpeg 424w, https://substackcdn.com/image/fetch/$s_!9dwM!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4678c086-a847-47fa-a48e-d4c4b37be9e0_1558x1247.jpeg 848w, https://substackcdn.com/image/fetch/$s_!9dwM!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4678c086-a847-47fa-a48e-d4c4b37be9e0_1558x1247.jpeg 1272w, https://substackcdn.com/image/fetch/$s_!9dwM!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4678c086-a847-47fa-a48e-d4c4b37be9e0_1558x1247.jpeg 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg role="img" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><title></title><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Source: <a href="https://theweek.com/political-satire/1023966/5-ominously-funny-cartoons-about-ai">theweek.com</a>. Image credit: Nick Anderson / Copyright 2023 Tribune Content Agency.</figcaption></figure></div><p>The process took me all day, and I felt like a novice juggler given fireballs and thrown into a live busker show. No one got burned, but my ego sure took a hit. </p><h2>How to bake normals in Blender</h2><p>In case you&#8217;re wondering, here&#8217;s the Blender normal baking process I followed<a class="footnote-anchor" data-component-name="FootnoteAnchorToDOM" id="footnote-anchor-1" href="#footnote-1" target="_self">1</a>.</p><p>&#8505;&#65039; <em>I&#8217;m using Blender 4.4 here</em>.</p><h3>Meshes and UV unwrapping</h3><ol><li><p>Create two meshes (two objects) that have the same basic size and position.</p></li><li><p>Leave one mesh as low-poly and add your details to the other, high-poly mesh.</p></li><li><p>UV unwrap the low-poly mesh and, in the <em>UV Editing</em> panel, name your texture image something like &#8220;NormalMap&#8221;.</p></li></ol><p>&#9888;&#65039; <em>Make sure you&#8217;re in </em>Edit<em> mode when working on the UVs, and in </em>Object<em> mode for all other steps. Otherwise, you might krangle things.</em></p><h3>Material</h3><ol><li><p>In the <em>Shading</em> editor, with the low-poly mesh selected, assign a new material.</p></li><li><p>Add an <em>Image Texture</em> node and set its linked image to the &#8220;NormalMap&#8221; you created above. Set the <em>Color Space</em> to <em>Non-Color.</em></p></li><li><p>Add a <em>Normal Map</em> node and link the <em>Color</em> output of the <em>Image Texture</em> you just added to the <em>Color </em>input of the <em>Normal Map</em> node. &#9995; Don&#8217;t connect the <em>Normal Map </em>output to anything yet (it can mess with the bake later).</p></li><li><p>Click the <em>Image Texture </em>node you added earlier and make sure it has a white outline. This designates the texture as the bake target.</p></li></ol><h3>Baking</h3><ol><li><p>In the <em>Layout</em> panel, select the high-poly object, <em>then</em> Ctrl + Click on the low-poly object (order matters here: you want the high-poly object selected and the low-poly object active). </p></li><li><p>In the <em>Render Properties</em> panel, make sure you have <em>Cycles</em> selected as the <em>Rendering Engine.</em></p></li><li><p>Go down to <em>Bake</em> and set the <em>Bake Type</em> as <em>Normal</em> and <em>Space </em>as <em>Tangent</em>.</p></li><li><p>Check <em>Selected to Active</em>, unfold it to see its suboptions, and set <em>Extrusion </em>to <code>1.0</code>.</p></li><li><p>Under <em>Output</em>, make sure the <em>Target</em> is <em>Image Textures.</em></p></li><li><p>Click the <em>Bake</em> button.</p></li></ol><p>If all went well, you should see a message saying, &#8220;Baking map saved to internal image, save it externally or pack it&#8221;.</p><h3>Viewing the bake</h3><ol><li><p>Heed the call: Return to your <em>UV Editing</em> panel and save the image to a file.</p></li><li><p>Go to the <em>Shading</em> panel and connect the <em>Normal Map</em> output to the <em>Principled BSDF Normal </em>input. </p></li></ol><p>Now, if you select either <em>Material Preview</em> or <em>Rendered</em> in the <em>Viewport Shading</em> options near the top of the window, you should see the low-poly model with your newly baked normal map.</p><h3>Some gotchas</h3><ul><li><p>If you see a &#8220;Circular dependency&#8221; warning when you bake, you may have left your <em>Normal </em>connected to the <em>Principled BSDF. </em>This trips Blender up, so it&#8217;s a good idea to disconnect the <em>Normal </em>from the <em>Principled BSDF</em> node when baking. Remember to connect it afterwards, though.</p></li><li><p>It&#8217;s probably a good idea to hide your high-poly model when previewing your baked normals. Otherwise, you risk confusing your high-poly geometry with the low-poly normal map.</p></li><li><p>If you&#8217;re not seeing all your high-poly geometry bake to your normal map, try exaggerating your high-poly bevels, insets, grooves, etc. You can also try fiddling with the <em>Bake</em> settings, specifically <em>Extrusion</em> or <em>Max Ray Distance</em>, or using a custom <em>Cage</em> object.</p></li></ul><h3>Exporting to GLTF</h3><p>I&#8217;m working on a three.js WebGL project, so I wanted a GLB (GLTF) export from Blender. If you&#8217;re doing the same, take care of the following to get your normal map exporting correctly.</p><ul><li><p>Add a <em>Triangulate</em> modifier to each object you&#8217;re exporting.</p></li><li><p>In the export settings, under <em>Mesh</em>, check <em>Apply Modifiers</em>, <em>Normals</em>, and <em>Tangents.</em></p></li></ul><p>Triangulating your meshes allows Blender to generate the tangent data needed at export time. Otherwise, three.js has to calculate this data at runtime.</p><h2>Annotated version</h2><p>To get the bake working took me all day. So like I mentioned earlier, this whole experience left me with a bit of a crisis of confidence. I&#8217;ve been thinking, &#8220;If I can&#8217;t do something as simple as baking a normal map without <em>this much trouble</em>, how can I ever hope to work in this field?&#8221;</p><p>Writing out the previous tutorial&#8212;which was not my intention when I sat down to write this post, by the way&#8212;I can see that it&#8217;s an involved process. I&#8217;m glad I wrote it all down for future reference. </p><p>I suppose I have some deeply held assumptions I can question. I believe I should learn things quickly. I did well at school for a period, and I think it got to my head. I&#8217;m embarrassed to admit that a family member once called me a &#8220;genius&#8221;. Of course, that&#8217;s an image I like to cleave to. But I don&#8217;t know that a label like that is useful or even accurate. </p><p>I guess I like seeing myself as smart and quick to proficiency. Without this often-held image, my deeply held belief that I am worthless begins to emerge. This is likely where a lot of my stress is arising from. Yet things take as long as they take. Proficiency in complex tasks comes with time and practice. </p><p>So here&#8217;s my mantra: Learn to be a beginner, to be OK with not knowing. To enjoy the process and let go of the outcome.</p><p>Who knows? </p><div class="footnote" data-component-name="FootnoteToDOM"><a id="footnote-1" href="#footnote-anchor-1" class="footnote-number" contenteditable="false" target="_self">1</a><div class="footnote-content"><p>Please feel free to correct my Blender bake normals recipe in the comments.</p><p></p></div></div>]]></content:encoded></item></channel></rss>