NoshBar's Dumping Ground






Get it here.

What you're getting


A Snake-type game where you are a short-sighted snake trying to find food in an unknown maze.

This prototype is unproudly delivered to you in the form of a thousand different hacks tied together with tape made from hack extract with a sprinkling of the worst "levels" ever "designed".

What I wanted to do


Well, for starters, "Short-sighted Snake" abbreviates beautifully to "SSS".
This is both often the onomatopoeia used for snakes AND an abbreviation for SubSurface Scattering... meaning I would have had the opportunity to go crazy with making 3 beautifully SSS rendered snakes next to each other to display the logo "SSS".

Title-screens aside, of course I wanted there to be a nice user interface for selecting levels, viewing scores, etc., but alas, I've just run out of the opportunity to be able to work on this any longer.

How to play


Upon loading the "game", use SPACE to start the game, then the arrow keys for changing direction of the snake.

As an added bonus hindering feature, you can also press "3" to view the level in pseudo-3D where the food sometimes becomes obscured by walls.

How to make levels


Should you one day lose your senses and decide you'd like to play this "game", you can make your own levels to replace the ones kindly provided in this distribution by Satan himself.
  • Levels are 32-bit PNG image files
  • Walls are defined by painting with a colour whose Alpha value is an even number
  • Upon startup, the game looks for consecutive files named "level1.png", "level2.png" and so on, until "level<N>.png" is not found.



[ view entry ] permalink print article

Or to be quite silly:
Delphi Web Scripting in a Dynamic Link Library for running Object Pascal scripts in C [and other languages]

What it is.


This is a simple Windows DLL (32-bit DLL provided) that enables you to compile and run Object Pascal scripts from within your favourite language (provided it supports loading DLL's with the stdcall calling convention) using the DWScript engine by Eric Grange.

Support for calling functions in the Pascal script is supported, as well as registering functions from e.g., C that the script can call. (A sample C wrapper and example are included in the "c_interface" folder).

Available under the Mozilla Public License 1.1

Why? Who can honestly say they've never wanted to run hand-optimised assembler inlined into Pascal Script from within Visual Basic 6? I know I have.

Features.


  • Run full Object Pascal scripts from within your application
  • Jitter can be enabled for JIT compilation, speeding up code "quite a lot".
    I obtained nearly double the execution performance in some cases e.g, running my smallPT renderer conversion without JIT enabled took 39 seconds, whereas the JIT enabled one only took 25 seconds.
    [*only when compiled with Delphi for now]
  • OLE support can be enabled
    [*only when compiled with Delphi for now]
  • ASM support can be enabled
    [*requires NASM executable in the same path as the DLL]
  • The provided DLL was built using Delphi XE 5 from an SVN checkout of the DWScript sources on the 18th of April 2014.


Using.


A simple C example would be something like this:
HMODULE handle = DWScript_initialise("dwscript.dll");  
//you can make as many contexts as you like, but cannot mix and match contexts as you wish
DWScriptContext context = DWScript_createContext(DWScript_Flags_Ole | DWScript_Flags_Asm);
//add any local C functions into the context with DWScript_addFunction()
//and DWScript_addParameter() before compiling
DWScript_compile(context, "begin end.", DWScript_Flags_Jitter); //only necessary once per context
DWScript_execute(context, DWScript_Flags_None); //call as many times as you like
DWScript_destroyContext(context);
DWScript_finalise(handle);


Ideas / TODO


  • Instead of the horrendous fixed-array of unions parameter nonsense going on, you could optionally make the functions take varargs and make calling them a much-more straight-forward affair.
    My only worry then is that you'd have to change from stdcall to cdecl, thereby losing the ability to use this DLL from within certain languages.
  • Fix Unicode/AnsiString conversions / Implement Unicode support
  • Add the ability to run a script in a non-blocking manner.
  • Add debugger support so that you can set breakpoints in the code, etc.
  • Make error handling and reporting not suck.


Free Pascal Notes.


TL;DR; Only this binary collection of FPC 2.7.1 works for me.

I initially started this project using Free Pascal.

As DWScript uses Generics, I needed a newer version of the Free Pascal compiler than what they provide on their home page (2.6).

Fortunately I had Laz4Android installed, which came with a build of FPC 2.7.1
This also provided me with the Masks unit that some DWScript units needed.
(I found mine in laz4android/components/lazutils)

I initially made some horrible hacks to the DWScript code to just get it compiling (deleting entire classes, casting wide to ansi strings, etc.), a simple proof-of-concept to see if it was worthwhile continuing.

Once I had a working DLL, I decided to update my version of Laz4Android to see if it fared any better at the Generics stuff...
Error: Undefined symbol: VMT_$DWSUTILS_$$_$GENDEF386

Hmm, Google had nothing on it, nothing on GENDEF386, couldn't find mention of this in the sources.
Oh well, no worry, I'll just try:
  • compiling FPC from SVN
  • CrossFPC
  • CodeTyphon
  • A random version of Laz4Android I found
  • Building it all on the command line using FPC, then linking it all manually with verbosity set to "I can show you the world"
...
Error: Undefined symbol: VMT_$DWSUTILS_$$_$GENDEF386
Well screw you too.

I've done some investigation into it, I built a little Python Pascal Parser to detect differentiating Interface/Implementation function descriptions and found some things... but nothing the compiler seems upset about.
So instead, if you want to use Free Pascal to compile this, you can try using the binary dump of FPC2.7.1 I took from my working version of Laz4Android from here.

[ view entry ] permalink print article

I recently discovered the HTML5 Canvas, it's lovely, like the good old days of using $A000:0000!

However, when drawing an image to the canvas it kept coming out all blurry. As it turns out, there are actually quite a few possible reasons for this to happen... here's a short checklist of what I discovered on my quest to fix it.

Setting Canvas dimensions



Most articles I came across mentioned that you should always explicitly specify the dimensions of a canvas, either when creating the element in bland HTML e.g.,
<canvas id="drawable" width="100px" height="100px"></canvas>

or via JavaScript e.g,
canvas        = document.getElementById("drawable");
canvas.width = window.innerWidth;
canvas.height = window.innerHeight;


Setting Canvas style dimensions



The above is actually not enough though, you also need to set the CSS dimensions, changing the above JavaScript to SOMETHING like:
canvas              = document.getElementById("drawable");
canvas.width = window.innerWidth;
canvas.height = window.innerHeight;
canvas.style.width = canvas.width.toString() + "px";
canvas.style.height = canvas.height.toString() + "px";


Catering for different pixel ratios



Testing my code out on my retina iPad, I discovered that window.innerWidth and window.innerHeight were returning half of what they should have.

Turns out there's a variable called window.devicePixelRatio that is present on retina devices, and contains the scale you should use when dealing with dimensions...

...sort of. See the "Drawing Pixels is hard" link below for a much clearer explanation.

CSS image rendering settings



Turns out there's ALSO a CSS variable you can change to affect how things are handled internally, it's called image-rendering

You can use it something like this:
/* applies to GIF and PNG images; avoids blurry edges */

img[src$=".gif"], img[src$=".png"] {
image-rendering: -moz-crisp-edges; /* Firefox */
image-rendering: -o-crisp-edges; /* Opera */
image-rendering: -webkit-optimize-contrast;/* Webkit (non-standard naming) */
image-rendering: crisp-edges;
-ms-interpolation-mode: nearest-neighbor; /* IE (non-standard property) */
}


Pixel offsets



Finally getting to what actually fixed it for me, a silly mistake to make.

I wanted to draw my image centered on the canvas, so ended up doing something like: x = canvas.width / 2 - image.naturalWidth / 2, doing the same thing for y.

This leads to floating point co-ordinates, perhaps starting in the middle of a pixel. Being a JavaScript dunce I simply used parseInt(x) to draw the image, and that seemed to cure it for me.

Oddly enough though, I've seen many mentions of always drawing to x+0.5,y+0.5, but I have no idea why you'd do that... unless you always happened to start at 0.5 in the first place.

References



Drawing pixels is hard

About the image-rendering setting


[ view entry ] permalink print article

Introduction


Calibre is handy for organising eBooks.
Stanza is really handy for reading eBooks on the iPad.
Calibre can act as an eBook server.
Stanza is capable of using this functionality to transfer books from your PC to your iPad.
Hooray, all my book-reading requirements are fulfilled!

*sigh*, of course not.

Stanza had a lot going for it: it was free; it could decode numerous eBook formats; it could download books from Calibre.
Sadly, it now has some issue: it is no longer available; with newer versions of iOS it has a bug where you can't navigate away from resized pages (well, you can, but it's a pain in the gluteus maximus).

As I personally only read books at home (not on holiday) I also found it a waste to have the eBook stored on my device, not only because of the space usage, but the Calibre-connection was really intermittent and unreliable and I'd rather count dust-bunnies on the floor than use iTunes to sync data.

The Stupid Idea


It is thus that I came up with another almost-patented stupid idea:
Make a remote Calibre eBook viewer, almost like a Calibre-VNC.
Make a tiny web-server that reads the Calibre database and feeds book information using JSON, and use a tiny WebApp that requests pages as images.
All processing happens on the server, so PDF pages are rendered to an image of the desired size and fed up as high-quality JPEG/PNG images to the WebApp.

This means that I no longer need to download books to my device, nor do I need to rely on the viewing application to cater for the format I want, as I can simply implement it on the server.
In theory, it means you could also read all your books from anywhere in the world via the internet, even if you forgot to sync it with your device.

The Prototype


As always, when I want to prototype something quickly, I turned to FreePascal/Lazarus.
Lazarus had everything I needed to test the idea:
  • a web-server class to server the JSON and images
  • a zlib class to open a test CBZ comic book
  • image classes to quickly load and resize JPEG images

Next I made a very hacky jQuery powered WebApp page thing to list books and navigate through a chosen book.
The web request "API" was very simple, you could ask how many pages a book had (/info/?id=10) or ask for a page from a book (/view/?id=10&page=13).
Next I made sure that the /view/ "command" supplied the dimensions of the current viewport so that became the native 1:1 "scale" for pages from the book.
The idea was that you could then zoom the 1:1 image locally in JavaScript, perhaps pan it around a bit, and then make another request to the server with a zoom factor, to clear the image up a bit.

I was set, it was all working pretty sweetly, so I went ahead and used libmupdf to test processing of PDF files, and... awesome.
It still has a minor issue where drawing the image to an HTML5 canvas results in it being blurry (despite setting the CSS dimensions to match, despite setting some custom moz and webkit filters), but -hey-, good enough for now.

The Proper Version


So, now it comes to making the "proper" version for people of the world to use, and I'm stuck.
I could make it in Python, but then people would have to install Python to get it to work... perhaps a non-issue?
I could make it in Mono just for my own fun, but again, it's another framework people need to install.
I could simply clean up the Lazarus version I guess, but there are a few niggly weird bits that I'd have to work around, and the resulting executable would be quite large.
I could make a plugin for Calibre, maybe?
I could make a plugin for Sumatra, maybe?
I'm tempted to do a very tiny version in C/C++ using the Mongoose web server library (Lua webpages? Woohoo!), JPEG compressor library and libmupdf... buuut that kind of thing always takes quite long to do properly.

This is all assuming that people would want to use this kind of thing and that I need to take it beyond the prototype...
But coding is fuuuun... can't... stop... self...


[ view entry ] permalink print article



Okay, this will be a short one, but I can't explain how disproportionately joyous I am having finally got shadows working in C.R.A.P.

It turns out I did NOT have to use shaders to do the shadows I wanted, as simple shadow volumes are sufficient to provide me with the sharp, clear shadows I wanted.
(I had finally taken the jump into learning shaders and actually got shadows working ... alright ... with them. But they were either too soft or jagged, and not "precise" enough).

Of course, I say "simple shadow volumes" when I really mean, well, they ARE simple, but there doesn't seem to be a quick explanation of how to calculate them. There are loads and loads of examples out there, each one showing the stencil mapping procedure you need to use, but most gloss over the calculation of the silhouette of the object in the first place.

Sure, if I'm doing stuff in 3D I should know what a dot product is and stuff, but I can't help but feel that there's space for a simplified explanation... one I may just make "soon".

Oh, and in the picture above, C.R.A.P. is currently keeping his cool in the slowly undulating waves of the water surrounding the city.
Yes, that's right, you can "swim"/float in the water, take THAT GTA 1 through (<4).

With the "water" and the shadows, everything is just looking and "feeling" so much better. I would even go so far as to describe things as "not so ugly".

[ view entry ] permalink print article

<<First <Newer | Older> Last>>