TinyCat [Lexaloffle Blog Feed]https://www.lexaloffle.com/bbs/?uid=56596 Obscurist's Cave <p> <table><tr><td> <a href="/bbs/?pid=146982#p"> <img src="/bbs/thumbs/pico64_obscurists_cave-3.png" style="height:256px"></a> </td><td width=10></td><td valign=top> <a href="/bbs/?pid=146982#p"> obscurists_cave</a><br><br> by <a href="/bbs/?uid=56596"> TinyCat</a> <br><br><br> <a href="/bbs/?pid=146982#p"> [Click to Play]</a> </td></tr></table> <br /> <del>load #obscurists_cave</del> Loading it this way does not seam to work for some reason? You can just use the png download.</p> <h3><strong>NOTICE</strong></h3> <p><strong>As of writing this, key() does not work in the web player. You can use arrow keys and right mouse button as substitutes for WASD and space. Otherwise, I would recommend playing on your own Picotron if you can</strong></p> <h2>CONTROLS - (requires mouse and keyboard)</h2> <ul> <li>WASD - left clump of buttons</li> <li>space - left lone button</li> <li>mouse - track ball</li> <li>left mouse button - right lone button</li> </ul> <h2>HISTORY</h2> <p>This is a port of a physical game/machine called Obscurist's Cave. Obscurist's Cave was made by Lynn Mathewson over the course of 2 years from 2005-2007 as one of his many side projects. Lynn would keep the device in the basement of his house for the next 9 years. After becoming hospitalized in 2016, Lynn would have the device donated to The Media Archaeology Lab, the local computer museum. Lynn insisted that a cassette of Negative Frequencies(1) be available to listen to as visitors played the game, saying that no other piece of music could better describe his mental state during the creation of Obscurist's Cave. Lynn died a later that year, on June 22nd. The device has required repairs, but is still in working condition as of 2024.</p> <p>(1) - <a href="https://urashima.bandcamp.com/album/negative-frequencies">Negative Frequencies can be found here on bandcamp</a></p> <h3>Lynn Mathewson</h3> <p>Lynn Mathewson was born 1953 Feb 13 in Bolder Colorado. At the age of 19 he began his studies in computer science at the Colorado School of Mines. He worked as a computer technician and repair man at the University of Colorado Boulder from 1975-2001. In 1993 Lynn bought a house with Suzanne Benson, a professor of forest ecology. In 2001 Suzanne would leave to Candida to follow her studies. Lynn said that his favorite places were the Into The Wind kite shop, and the street he grew up on as a kid.</p> <h3>The Device</h3> <p>The device is made from recycled computer parts, as well as other custom made componentry. It weighs close to 100 pounds because of two car batteries that allow the device to be played continuously, for about a week without recharge. Otherwise the device can last quite a long time without user input. While no user input is being given, the device will stop making certain calculations, putting itself into a stasis. After 30 minutes the device will completely shutdown, and can be awakened by pressing any of its buttons. After the 9 years it had been in the basement of Lynn's house, the device able to stay active for a couple minutes before it had to be recharged. The screens are custom made e-ink, helping with this low power consumption. The device does not have a power switch, and the state of the game is always being backed up. When The Media Archaeology Lab received the device, the player was in a very strange position within the game world. It took a while to figure out how to reset the game to its &quot;starting&quot; positions. The volunteers weren't sure if there was even a supposed starting position.</p> <h3>Interpretations</h3> <p>The interface and puzzles of Obscurist's Cave have been described as obscure, while still being a playable experience. As for what meaning could be drawn from the game, some have said its just a strange puzzle game, while others have sworn by the game's ability to whisk them away, putting them into an unsettling headspace.</p> <h3>DEV'S NOTE - Elijah Bennett</h3> <p>I work as a volunteer at The Media Archaeology Lab, that's how I was introduced to Obscurist's Cave. Found this game to be overly cryptic for how much &quot;secret&quot; it had to reveal. I'll spoiler it for those who care -&gt; It requires that you know...<div><div><input type="button" value=" Show " onClick="if (this.parentNode.parentNode.getElementsByTagName('div')[1].getElementsByTagName('div')[0].style.display != '') { this.parentNode.parentNode.getElementsByTagName('div')[1].getElementsByTagName('div')[0].style.display = ''; this.innerText = ''; this.value = ' Hide '; } else { this.parentNode.parentNode.getElementsByTagName('div')[1].getElementsByTagName('div')[0].style.display = 'none'; this.innerText = ''; this.value = ' Show '; }"></div><div><div style="display: none;">...how ASCII works, and how negative numbers are represented in integers.</div></div></div> Usually i find its best if the whole &quot;puzzle&quot; is self contained. I did however find it quite an interesting game to deconstruct and re-program to work on Picotron. I learned a lot about how 3d math is done at a low level: collision, fish-eye camera, matrix multiplication for rotations.</p> <h2>FISHEYE</h2> <p>The fisheye rendering is done in the following steps.</p> <ul> <li><em>TRANSFORM</em> the points, offset by the camera's position and rotated by the camera's rotation.</li> <li><em>NORMALIZE</em> this new vector.</li> <li><em>IGNORE THE Z</em> component of the vector, just use x and y for screen position.</li> <li><em>RENDER THE CURVES</em> between each point in the tri </li> </ul> <img style="margin-bottom:16px" border=0 src="/media/56596/19_Untitled.png" alt="" /> <p>Rendering the tri is definitely the hardest part. First, lets figure out what the shape of the tri is.</p> <img style="margin-bottom:16px" border=0 src="/media/56596/21_Screenshot_2024-04-19_18-54-38.png" alt="" /> <p>Here you have the tri's main points, <em>Red, Green, Blue</em> creating a clockwise triangle. We can define this initial curve as such...</p> <div> <div class=scrollable_with_touch style="width:100%; max-width:800px; overflow:auto; margin-bottom:12px"> <table style="width:100%" cellspacing=0 cellpadding=0> <tr><td background=/gfx/code_bg1.png width=16><div style="width:16px;display:block"></div></td> <td background=/gfx/code_bg0.png> <div style="font-family : courier; color: #000000; display:absolute; padding-left:10px; padding-top:4px; padding-bottom:4px; "> <pre>curve = { { v = vec(tri[1].x, tri[1].y, tri[1].z), next_i = 2 }, { v = vec(tri[2].x, tri[2].y, tri[2].z), next_i = 3 }, { v = vec(tri[3].x, tri[3].y, tri[3].z), next_i = 1 }, }</pre></div></td> <td background=/gfx/code_bg1.png width=16><div style="width:16px;display:block"></div></td> </tr></table></div></div> <p>The between points are what make the fish-eye effect all nice and curvy. These midpoints are made in the following steps.</p> <ul> <li>Get the mid-point between a point and its next point.</li> <li>Normalize this mid-point, this is what creates the curve.</li> <li>Check if the distance (is screen space) between our first point and this normalized mid-point is smaller than a certain threshold. If it is, we move on to the next point in our chain. If not, we repeat this process.</li> </ul> <p>Now I only had to deal with wire-frame. I just draw lines between the points. If we wanted to rasterize these convex shapes maybe something like this would work -&gt; <a href="https://www.youtube.com/watch?v=SO83KQuuZvg">Coding Adventure: Rendering Text</a></p> <h3>thanks for reading :)</h3> <p>All of the stuff in the history section is of course fictional. Just some ARG fun.</p> https://www.lexaloffle.com/bbs/?tid=141831 https://www.lexaloffle.com/bbs/?tid=141831 Sat, 20 Apr 2024 14:51:38 UTC cat in snow <p> <table><tr><td> <a href="/bbs/?pid=139066#p"> <img src="/bbs/thumbs/pico8_catinsnow-3.png" style="height:256px"></a> </td><td width=10></td><td valign=top> <a href="/bbs/?pid=139066#p"> cat in snow</a><br><br> by <a href="/bbs/?uid=56596"> TinyCat</a> <br><br><br> <a href="/bbs/?pid=139066#p"> [Click to Play]</a> </td></tr></table> </p> <p>a cozy lill' walk through some snowy woods<br /> this game is mostly about atmosphere, so no objectives here. just walk around till you feel done :)</p> <p><img style="margin-bottom:16px" border=0 src="/media/56596/8_catinsnow_cover_image.gif" alt="" /> <img style="margin-bottom:16px" border=0 src="/media/56596/13_game_preview_2.gif" alt="" /></p> <h1>the trees</h1> <p>i'm real happy about how natural the tree generation feels so i figured i'd talk about it.<br /> the trees start out like this.</p> <img style="margin-bottom:16px" border=0 src="/media/56596/15_Untitled.png" alt="" /> <p>the main thing that helps sell the forest is the random tree placement. but if we just did something like..</p> <div> <div class=scrollable_with_touch style="width:100%; max-width:800px; overflow:auto; margin-bottom:12px"> <table style="width:100%" cellspacing=0 cellpadding=0> <tr><td background=/gfx/code_bg1.png width=16><div style="width:16px;display:block"></div></td> <td background=/gfx/code_bg0.png> <div style="font-family : courier; color: #000000; display:absolute; padding-left:10px; padding-top:4px; padding-bottom:4px; "> <pre>tree.x = x + RND(8) - RND(8) tree.y = y + RND(8) - RND(8)</pre></div></td> <td background=/gfx/code_bg1.png width=16><div style="width:16px;display:block"></div></td> </tr></table></div></div> <p>..then each time we re-spawn the trees for a area they would be in different spots then before. basically we need a function that returns a sudo random value <code>y</code> from value <code>x</code>. thats were this function comes in...</p> <div> <div class=scrollable_with_touch style="width:100%; max-width:800px; overflow:auto; margin-bottom:12px"> <table style="width:100%" cellspacing=0 cellpadding=0> <tr><td background=/gfx/code_bg1.png width=16><div style="width:16px;display:block"></div></td> <td background=/gfx/code_bg0.png> <div style="font-family : courier; color: #000000; display:absolute; padding-left:10px; padding-top:4px; padding-bottom:4px; "> <pre>FUNCTION ConstRnd(_𝘹,_𝘳) IF _𝘳 == NIL THEN _𝘳 = 1 -- r meaning range END RETURN (COS(_𝘹*.6)+SIN(_𝘹*4.9)+SIN(_𝘹*.01)+COS(_𝘹*7.3))/4*_𝘳 END</pre></div></td> <td background=/gfx/code_bg1.png width=16><div style="width:16px;display:block"></div></td> </tr></table></div></div> <p>here's a part of the function on desmos..</p> <img style="margin-bottom:16px" border=0 src="/media/56596/function.png" alt="" /> <p>so while not totally random, it looks random enough :)<br /> so instead we do something like this</p> <div> <div class=scrollable_with_touch style="width:100%; max-width:800px; overflow:auto; margin-bottom:12px"> <table style="width:100%" cellspacing=0 cellpadding=0> <tr><td background=/gfx/code_bg1.png width=16><div style="width:16px;display:block"></div></td> <td background=/gfx/code_bg0.png> <div style="font-family : courier; color: #000000; display:absolute; padding-left:10px; padding-top:4px; padding-bottom:4px; "> <pre>tree.x = x + ConstRnd(y) tree.y = y + ConstRnd(x)</pre></div></td> <td background=/gfx/code_bg1.png width=16><div style="width:16px;display:block"></div></td> </tr></table></div></div> <p>the reversal of x and y is important, otherwise we get this banding effect..</p> <img style="margin-bottom:16px" border=0 src="/media/56596/bad_trees.png" alt="" /> <p>beyond that, its just a matter of scaling the top of the tree with <code>SSPR</code>, placing some random sets of branches, and doing some random flipping of the tiles.</p> <img style="margin-bottom:16px" border=0 src="/media/56596/finished tree.png" alt="" /> <h2>links</h2> <p>an archive of the dev files can be found on <a href="https://es5000.itch.io/cat-in-snow">the itch.io page</a><br /> was made as part of the <a href="https://itch.io/jam/secret-santa-2023">2023 Secret Santa game jam</a></p> https://www.lexaloffle.com/bbs/?tid=55449 https://www.lexaloffle.com/bbs/?tid=55449 Sun, 24 Dec 2023 01:16:05 UTC