[HN Gopher] How I made a 3D game in 2 KB of JavaScript ___________________________________________________________________ How I made a 3D game in 2 KB of JavaScript Author : pjmlp Score : 330 points Date : 2020-03-09 10:30 UTC (12 hours ago) (HTM) web link (frankforce.com) (TXT) w3m dump (frankforce.com) | m00dy wrote: | damn, | | I was reading the blog post and mistakenly refreshed the page. | Now, BW is exhausted. I didn't know... | 6510 wrote: | It looks great, runs smoothly but I'm not having a gameplay | experience. | notkaiho wrote: | What do you mean by a 'gameplay experience' in this case? | 6510 wrote: | I don't want to hate on the creation at all but its hard not | to sound like that in text. | | On commodore 64 games tried to have nice graphics, nice music | and interesting mechanics. Lots of games failed at 1 of the | 3. Sometimes they did really well with the other challenges | but with few exceptions it doesn't make up for it. | | I think if 2 kb is the challenge the game mechanics are the | best hope to make up for the lack of sound and visuals. | | Reminds me of burning rubber. A game with truly ugly graphics | and terrible music that is quite hilarious to play. | | https://www.youtube.com/watch?v=nKSbOyGy_Qo | egypturnash wrote: | ...which is a shameless clone of Data East's Bump 'n' | Jump/Burnin' Rubber, which had much better art and sound. | https://m.youtube.com/watch?v=99gnxjpeL7s | 6510 wrote: | haha, so they kept only the game play. It makes a lot | more sense now. | mosselman wrote: | The game is pretty fun and playable for its size. Nice work! | throwaway77384 wrote: | I absolutely love projects like this. It's so interesting working | within these constraints. | | So, js1k is not continuing? On the js1k site I can't see anything | stating this. Nothing on the subreddit either. Where is that | information coming from? | | It's a real shame that this great tradition may not continue, | though, perhaps the js2k+ will be the next big thing ;) | woogley wrote: | Only thing I can find is this tweet from the organizer. | https://twitter.com/kuvos/status/1213546333707083778 | pjmlp wrote: | Love the WASM remark on his tweet. | | Think WASM coding like the original Demoscene demos. | tracker1 wrote: | Not sure about the 2k+zip, but I do think that there will | be a _LOT_ of progress in wasm+canvas for interactive | programming... of course this leaves out accessibility, so | hopefully it 's done with some constraint depending on the | space. | sccxy wrote: | Controls: | | Mouse = Steer | | Click = Brake | | Double Click = Jump | | https://github.com/KilledByAPixel/HueJumper2k | iron4o wrote: | Why are there trees in them middle of the road? ;D | KilledByAPixel wrote: | Alien trees... | franblas wrote: | Nice ! :) Looks like a raycasting engine like this one | https://www.playfuljs.com/a-first-person-engine-in-265-lines... | KilledByAPixel wrote: | Nope! It is not a raycasting engine at all, but instead built | similar to old school racing game tech. | winrid wrote: | Could you help us understand how it's not ray casting? OP | doesn't mean ray tracing by the way. Ray casting is the tech | used in Wolf3D for example, or maybe I'm preaching to the | choir. | fenwick67 wrote: | Since the car only goes forward, there's no reason to have | any depth or visibility testing, things are just rendered | in order (painter's algorithm). | KilledByAPixel wrote: | With ray casting engines for each column of pixels you cast | a ray and collide it against world geometry to see what it | hit and where. | | With this engine, and most modern 3d engines you apply a | transform to 3d world space points to get a screen space | point. You also need to sort objects by distance or use a z | buffer. | notkaiho wrote: | And thanks to this article I've learned about the Google Closure | compiler: https://developers.google.com/closure/compiler | Cthulhu_ wrote: | Is it still relevant and updated nowadays? IIRC that one's been | around for at least a decade already. | lvh wrote: | Absolutely. It took a long time for everyone to catch up on | basic features (Closure had modules figured out while the | rest of the JS community still had several competing | standards), but it's still tremendously effective. | | The only downside is the compiler itself runs on the JVM, and | most developers ostensibly prefer a single platform. Given | how much other software you need to make a development | environment work, this seems silly to me. | nathell wrote: | There is a JavaScript port of the Closure compiler, | available from npm: https://www.npmjs.com/package/google- | closure-compiler | Scarbutt wrote: | A real downside and the reason it never took off, is that | you have to annotate all your Javascript code to really | leverage the Closure compiler. | | Google also doesn't really advertised the use of Closure, | you have to go out of your way to find it in their | developer website or google it to find it. It's really just | an internal tool. | | They break backwards compatibility in the Closure Library | so much that projects that adopted Closure (like | Clojurescript), are stuck with a library from 2017. The | project is maintained only to serve Google. | nathell wrote: | > They break backwards compatibility in the Closure | Library so much that projects that adopted Closure (like | Clojurescript), are stuck with a library from 2017. The | project is maintained only to serve Google. | | Is that the case? The current version of ClojureScript | depends on org.clojure.google-closure-library | 0.0-20191016 - I know it's a fork, but I'm not sure to | what extent it is being synced with upstream. | Scarbutt wrote: | Their repo says they are using version | "0.0-20170809-b9c14c6b" | | https://github.com/clojure/clojurescript/blob/master/deps | .ed... | | https://github.com/clojure/clojurescript/blob/master/proj | ect... | jyriand wrote: | ClojureScript leans heavily on google closure. | Scarbutt wrote: | yes, but since we are talking about size, a hello world | Clojurescript is going to be at least 80KB or greater. | jfkebwjsbx wrote: | I love these projects, but writing statements like "full HD" and | "Realistic driving physics and collisions" is a bit too much | unless it is tongue-in-cheek :) | KilledByAPixel wrote: | HD because many tiny games like this do not stretch to fill the | whole window. It requires extra code to do this and have | everything scale properly. | buzzerbetrayed wrote: | I've never heard "HD" be used to mean "full width" | chipperyman573 wrote: | I haven't either but as someone who plays games | occasionally, the definition makes sense to me (lots of | games don't scale well). Definitely not something I'd have | guessed, though. | recursive wrote: | It's "high definition". Since the graphics are all vector | graphics, it doesn't seem to be too far of a stretch. All | the rendering will be done at the resolution available. | KilledByAPixel wrote: | Do you have an HD monitor? If so the game is in HD. Many | tiny games and demos like this are rendered to a smaller | canvas and will either not stretch to fill your monitor or | are rendered at a lower then HD resolution. | jfkebwjsbx wrote: | When people use that term for games, it usually means the | assets have been reworked to look better. | | In this case, I guess that would be the procedural | generation of the background and trees, for instance, to | give it better quality than simple triangles. | jsgamedev wrote: | This is very impressive! | | Lots of counterintuitive observations when you realize the | objective is for compressed 2k size, which means that duplicate | code is actually a good thing! | | It reminds me of this 3d maze in 1k of javascript from many years | ago: https://js1k.com/2010-first/demo/459 | KilledByAPixel wrote: | Thanks, I also referenced this jk1k racing game in the post... | | https://js1k.com/2019-x/demo/4006 | aylmao wrote: | In the final, minified code there's a lot of calls to Math | methods (sin, cos, tan). I wonder if there's potential to shrink | this even more with some assignments: | M=Math,s=M.sin,c=M.cos,p=M.PI,a=M.abs; // etc. | nathell wrote: | Also in the genre of tiny racing games, this 2004 entry from | IOCCC comes to mind: | | https://www.ioccc.org/2004/vik1.c | agys wrote: | In the minified code there are still a lot of Math.PI, Math.sin, | Math.cos... could this not be optimised further with something | like s=Math.sin...? | cjg wrote: | It gets zipped so the duplication goes away. In fact, | repetition is deliberate to get better compression. | Elrac wrote: | In the original article, the author claims that lots of | repeated strings turn out to be beneficial insofar as they make | compression (gzip or whatever) more effective. According to | him, it doesn't make sense to manually de-redundantize code | when the compressor will achieve the same gain or better. | vanderZwan wrote: | I was about to say _" well, it's probably a lot of work to | verify that s isn't already a mangled variable name"_ but then | I realized that doing what you suggested in the pre-minified | code should work, yeah. | | So not only are you right, it's actually super easy. Just do | this at the top level of your code: const | {cos, sin, PI /* etc */} = Math; | [deleted] | KilledByAPixel wrote: | You could do that, but it would not compress as well. For | example the word const is not use anywhere in the 2k version, | while Math. is used about 40 times so it becomes essentially | free when compressed. | vanderZwan wrote: | > _For example the word const is not use anywhere in the 2k | version, while Math. is used about 40 times so it becomes | essentially free when compressed._ | | Except that the word const does seem to be used in the | uncompressed version, so we don't know what happens during | compression in the Closure compiler, no? Or is the 2k | version pre-Closure compiler different from the | uncompressed version? | | Either way the only way to know is to try because | asymptotically free is all well and good, but without | measurement we don't know the actual behavior in practice | and we are just making assumptions about how well or how | badly things compress and how the mangling process works | out. | KilledByAPixel wrote: | Ok, I just tried it. Removing every Math. and adding | let{cos,sin,PI,min,max,tan,atan2,abs,ceil}=Math; to the | top. It worked better then I expected, though it is still | 1 byte larger then without. Could potentially be a win in | some situations. | vanderZwan wrote: | Nice! Thanks for trying! | | > _it is still 1 byte larger then without_ | | That's actually pretty cool, because together with your | earlier remark of ~40x occurrences of Math.<whatever> | that means we have a ballpark figure for where the | tipping point is! | pettycashstash2 wrote: | resource limit reached..... | midgetjones wrote: | Seems to be struggling a bit. Alternate link: | https://web.archive.org/web/20200309074327/http://frankforce... | itronitron wrote: | here is the codepen link from same article >> | https://codepen.io/KilledByAPixel/pen/poJdLwB | TruthSHIFT wrote: | FYI, there is no jump button. Also, those are rocks, not | ramps. Jumping is not a gameplay mechanic in this game. | KilledByAPixel wrote: | Double click to jump. | krossitalk wrote: | Thanks. Wish the controls were more obvious. After | learning this the game is actually quite playable. | huskyr wrote: | "Resource Limit Is Reached", seems a bit silly for a 2kb game | ;) | techntoke wrote: | Should call it "How I host my website for $2 a year." | huskyr wrote: | For $2 a year i think you could manage 2kb ;) | dlsso wrote: | Makes you wonder if the 70gb installs of modern games are really | necessary. | | Also, obligatory kkrieger link: | https://en.wikipedia.org/wiki/.kkrieger | ssully wrote: | It's an impressive project, but it shouldn't make you question | why games are so large these days. | KilledByAPixel wrote: | I think there is a middle ground of many indie games I see on | steam that are much larger then they should really be. | | As a dev, one problem I saw often is UE4 is massive, well | over a hundred meg for just the base engine. | meheleventyone wrote: | Binary size is a drop in the ocean most of the size of game | installs is in assets. | Sohcahtoa82 wrote: | While true, you do have to ask how the hell there could | possibly be 100 MB of _just code_. | | Consider Windows calculator. In Windows 10, it consumes | 15+ MB of RAM. When desktops have 8+ GB of RAM, 15 MB is | essentially nothing. And yet, 15 MB is an astronomical | amount of RAM considering the functionality Calculator | offers. There's really no reason it should be more than a | couple hundred kilobytes. | austincheney wrote: | Makes you wonder if the nearly half gigabyte software kits are | really necessary to make a simple website. I am looking at you | Angular and React. | Goronmon wrote: | My non-expert opinion is that the size of most game installs is | tied directly to the amount of voiced dialog in the game, and | in a similar context, how many languages that voiced dialog has | been translated and included in the install. | tabtab wrote: | I made a 2D game in 3 KB of JavaScript. Not quite as impressive I | suppose. | IvanK_net wrote: | It reminds me my 3D demo in 47 lines of JS (without WebGL) :) | https://jsfiddle.net/06L845jx/86/ | | And 54 lines of JS: https://jsfiddle.net/06L845jx/127/ | numlock86 wrote: | > It reminds me my 3D demo in 47 lines of JS | | How exactly? | KilledByAPixel wrote: | That's cool! Reminds me of pavel's 1 line cube tornado. | | https://www.dwitter.net/d/14485 | rsiqueira wrote: | The first ideas of this 3D road game was created in just 140 | characters (or less) and posted here (Dwitter) by him (Frank | Force's nickname is "KilledByAPixel"): | https://www.dwitter.net/h/road And many other tiny 3D effects and | engines in JavaScript were created by Dwitter's users, like these | demos: https://www.dwitter.net/h/d3 | tomxor wrote: | Hi Rodrigo! | | Just wanted to add... Dwitter is awesome for learning stuff | like this, since everything is so absurdly small you know the | ceiling of time required for understanding a dweet is pretty | low - yet at the same time it's surprising how advanced | techniques can get in this tiny space. | | This makes them so tempting. I sometimes struggle to pick up or | return to a technical book when work/life etc gets busy, but | when someone posts an interesting new dweet I often can't stop | myself from pulling it to pieces. ___________________________________________________________________ (page generated 2020-03-09 23:00 UTC)