HN user

t0mek

663 karma

Site: tomek.rekawek.eu Blog: blog.rekawek.eu

Posts9
Comments80
View on HN

I like the "challenges" part at the end, especially the varying difficulty levels:

* A quadratic formula program, which outputs the number of roots and the x-intercepts upon the user inputting the values of A, B, and C.

* A fighting game, with health, a store, different enemies, weapons, armor, etc, with graphics and animation.

Only tangentially related (but hey, it's HN) - I'm so happy about the support/requirements for trailing commas in the modern language syntax:

    x = [
      123,
      456,
      789,
    ];
It makes editing such a list so much easier. Also, the commit diffs are cleaner (you don't need to add comma to the last element when appending a new one).

Not a tutorial per-se, but here are 2 slides describing how I've done it:

https://www.slideshare.net/slideshow/emulating-game-boy-in-j...

Essentially, there are 4 channels, each providing a number 0-15 on every tick. Emulator should mix them together (arithmetic average), scale up to 0-255 and feed to the sound buffer, adjusting the tick rate (4.19MHz) to the sound output rate (e.g.: 22 kHz) - taking every ~190 value (4.19MHz / 22 kHz) is a good start.

Now the 0..15 value that should be produced by each channel depends on its characteristics, but it's well documented:

https://gbdev.gg8.se/wiki/articles/Gameboy_sound_hardware

Channels 1 and 2 produce square waves, so a bunch of low (0) and high (15) values, with optional volume envelope (gradually going down from 15 to 0 on the "high" part of the square) and frequency sweep (alternating 0s and 15s slower or faster).

Channel 3 allows an arbitrary waveform, read from the memory.

Channel 4 is a random noise, generated by the LSFR.

See SoundModeX.java for the reference:

https://github.com/trekawek/coffee-gb/tree/master/src/main/j...

I've always seen A600 more like a budget version of A1200 rather than a new variant of A500: better graphics chip, IDE port, PCMCIA and new look-and-feel of the Workbench 2.04 (at the first sight hardly distinguishable from the Workbench 3.0) gave a taste of something new.

12 years ago, when we already had Arduino but no ESP32 yet, I built this thing:

https://newton-net-pl.translate.goog/2012/01/robot/?_x_tr_sl...

It was made of an old HTC Magic phone, acting as camera+wifi transmitter, connected to Arduino via its serial port and level shifter, to control the servo and a RGB LED. I had a lot of fan with that, even if the connection wasn't really to stable.

Thanks for sharing, maybe it's time to revive the project with the next generation of the microcontroller.

Yes, the liar have some hats. There are two ways how to conclude this:

1. If they don't have any hats, then any sentence about them would be truth.

2. The negation of the sentence, which must be truth, is "not all my hats are green". For this to be true, there must be some hats that are not green, so there must be some hats in general.

Programming a chess program was an important challenge for the "first generation of hackers" working on the mainframe machines like TX-0 and PDP-1 in '50 and '60, as described in "Hackers: Heroes of the Computer Revolution" by Steven Levy. I highly recommend this book, I think a lot of people here can recognize their own passion and interests in the stories described there.

Also, there's interesting implementation for the ZX-81, created over 20 years later and fitting in just 1024 bytes: https://users.ox.ac.uk/~uzdm0006/scans/1kchess/

We can also assume that the p/q=√2 is already the simplest form of the fraction, since every fraction must have one, as in the first section of the article.

Then if we figure out that both p and q are even, it means that p/q can be simplified (by dividing p and q by 2), which contradicts the assumption about the simplest form - and we don't need to use the infinite descent.

A few years ago, I spent a fair share of time trying to copy files from and to a Macintosh Plus. I decided to use a 100 MB ZIP drive (actually two of them, SCSI for the Mac Plus and USB for a modern computer) and later a serial port connection with terminal software [1].

Now there's a much better and cheaper option: BlueSCSI [2]. It's a SCSI HDD emulator that allows to mount .img files stored on a SD card as HDD disks. It also supports CD and network card emulation.

Once the files are copied on a such a virtual drive, they can be extracted on a modern machine using via some kind of HFS explorer or an emulator.

[1] https://blog.rekawek.eu/2016/12/08/mac-plus#hard-drive

[2] https://bluescsi.com/

I remember having similar effects after long sessions of Lemmings. I saw the damn rodents when I was closing my eyes in bed, but it didn’t disturb my sleep (I guess they acted as sheeps to count).

Procedural generation was also used to generate levels in the Pitfall game for Atari 2600. A single level was represented with a byte (!) and bits were controlling the number of rolling logs, holes, etc. There were 255 levels there and LFSR was used to go from one level to another, so the actual level bytes wasn't even stored in the ROM.

For more details and screenshots see this great blog post: https://evoniuk.github.io/posts/pitfall.html

https://aqi.eco/

Open-source, crowd-sourced air quality page. I’m running it for 3 years now. Owners of private air quality detectors can use it to built micro-communities in their neighbourhoods. Eg. organization registered at https://mosina.aqi.eco installed dozens of sensors in their home town and is advocating for improving the air quality there.

Around 13k unique users and 40k sessions per month. Cost is about $35 for VMs and storage on DigitalOcean.

although organizing it like a virtual FileSystem does have a certain appeal, and unfortunately I don't know of a database engine that supports such a layout

Apache Jackrabbit Oak [1] implements a tree-format data model called JCR [2]. It's used as database engine for the Adobe Experience Manager (enterprise-level CMS).

[1] https://jackrabbit.apache.org/oak/docs/ [2] https://en.wikipedia.org/wiki/Content_repository_API_for_Jav...

This approach is very similar to the way how Kubernetes custom resource reconciliation works (and Kubernetes in general, but the custom resources is the way how you can bring your own logic there).

In Kubernetes you can define your own types, Custom Resources (basically JSONs with schema) and deploy "operators" - services that should handle these new types. Every time you create or modify your custom resource, the operator is triggered and it should "reconcile" your resource.

Now this reconciliation process is stateless. It doesn't know what exactly changed in your resource, so it should just go through the list of all the things that it needs to do (create or remove pods, services, configmaps, etc.) and if something is not right (e.g. a missing service), try to make it right or fail. In any case, the output should be written in the custom resource's .status section.

There's no active waiting - if the operator sees that some other resource is not ready yet (a required pod is still starting), it should just mark your resource as not ready and finish. If the pod state changes, the next reconciliation will notice it. It should do as much as it can to bring reality to the expectation, but not more.

If implemented correctly, this is surprisingly resilient. The idempotent nature of the reconciliation loop makes it perfect for errors handling. For instance, your reconciliation may fail because some pod is not running correctly. It's nothing that your operator can fix. But if the pod auto-heals (maybe the network connectivity was restored or an external service is available again), the operator will auto-heal as well, without a manual intervention. The next reconciliation loop will just see the pod is available again and carry on.

Developers should exercise caution when typing npm commands in the terminal when especially when using flags.

The double ”when” is quite funny here, given the nature of npm problem described in the article.

"Another World", the game, is an interesting example of this approach. It's implemented in a mini-VM, with 29 opcodes - apart from the low-level "mov", "call", "ret", etc. there are high-level ones too, like "fill fb" or "draw txt". The VM design was closely related to the art style of the game, based on polygons, not bitmaps.

With this approach it was fairly easy to port the game to various platforms. "Only" the VM implementation had to be ported, while the bytecode remains the same. Of course, the VM implementation had to be tied to the graphics and sound subsystems of the target platform.

There's a super-interesting series of blog posts, starting with [1], describing the "Another World" internals and also the design of all the platforms to which it was ported: Amiga, Atari ST, PC, Genesis, SNES and GBA.

[1] https://fabiensanglard.net/another_world_polygons/index.html

A similar observation is that there's exactly as many natural numbers [0, 1, 2, 3, ...) as integer numbers (the same, but with negatives: ..., -2, -1, 0, 1, 2, ...).

Normally we'd need to count things to say there's "as many" X as Y. But with infinities counting is a bit tricky. So, is the infinite count of natural numbers the same kind of infinity as count for integer numbers?

To check this, we need to see if for every number in one set we can assign exactly one number in the other set (and the other way around). It's actually pretty simple:

    0 -> 0
    1 -> -1
    2 -> 1
    3 -> -2
    4 -> 2
    5 -> -3
    6 -> 3
    ...
Since this mapping ("bijective function") exists, we know that every number in one set has exactly one representative in the other set - so the set counts are identical.

What's interesting, if we look into real numbers (think: double in C, but without problems with approximation), there's much, much more of them. The infinite count of real numbers is much larger than the infinite count of integers. But let's keep it for another comment.

The infinity is an important concept which appears in most areas of the maths and physics. The maths is full of ideas that may seem counterintuitive (eg. "imaginary unit" - the square root value of -1), but as long as they are precisely defined, they can be used in reasoning that gives practical results.

And even if some math concepts can't be applied to anything practical yet, we never know what will be used to formulate another theory about the stock market behaviour or processes inside the black hole.

Coming back to your question, here's an example: many math constants (pi, e) and functions (sin, cos) can be defined as infinite sums (series). They converge, getting closer and closer to the limit, but they never achieve it.

Using these series it's possible to calculate (in a calculator, Excel, Quake or CAD) values of these functions with any required precision.