release winning entries of IOCCC28 under the year 2024
Congratulations to: * 2024/anders - Prize in sound coding - layered music generator * 2024/burton - Prize in pentagrammatology - wordle hard mode solver * 2024/cable1 - Prize in bot talk - LLM inference engine * 2024/cable2 - Prize in murky waters - salmon recipe * 2024/carlini - Prize in perfect timing - Intel 4004 emulation * 2024/codemeow - Prize in tray planting - bonsai generator * 2024/endoh1 - Prize in patient pointillism - slow ray tracer in CPP * 2024/endoh2 - Prize in solid body physics - rotating rigid body simulation * 2024/ferguson1 - Prize in diabolical logistics - Oregon trail pact with the devil * 2024/ferguson2 - Prize in yil-tas - Navajo code talker translator * 2024/howe - Nice accent eh-ward - mini vi * 2024/kramer - Prize in linguistic arithmetic - natural language numerical calculator * 2024/kurdyukov1 - Prize in phased periodicity - phase of the Moon * 2024/kurdyukov2 - Prize in art restoration - JPEG artifact removal * 2024/kurdyukov3 - Prize in virtual quietus - gaming VM and doom * 2024/kurdyukov4 - Prize in embiggening - encode without literals * 2024/maffiodo - Prize in creative interpretation - Jav\*script interpreter * 2024/mills - Prize in ℤ₃ - Infocom v3 story interpreter * 2024/stedolan - Best one liner - icon from MD5 * 2024/straadt - Prize in imitative rebooting - OpenRISC CPU and Linux * 2024/tmarrec - Prize in cyclonic coding - 3D tornado simulation * 2024/tompng - Prize in quasi bijection - vortex encryptor decryptor * 2024/weaver - Sur prize - rickroll Ran `make update` to perform the above. new file: 2024/burton/.entry.json
This commit is contained in:
1 parent
10512e6c79
commit
09750f8899
443 files changed
+182938
-231
No files matched your search
@@ -0,0 +1,275 @@
|
||||
## To build:
|
||||
|
||||
``` <!---sh-->
|
||||
make all
|
||||
```
|
||||
|
||||
|
||||
## To use:
|
||||
|
||||
``` <!---sh-->
|
||||
./prog < body.txt
|
||||
```
|
||||
|
||||
|
||||
## Try:
|
||||
|
||||
``` <!---sh-->
|
||||
./try.sh
|
||||
```
|
||||
|
||||
|
||||
## Judges' remarks:
|
||||
|
||||
Playing with this entry, we were able to experience joy akin to
|
||||
[what Niels Bohr and Wolfgang Pauli could have experienced when they played with the Tippe-Top](https://repository.aip.org/wolfgang-pauli-and-niels-bohr-demonstrating-tippe-top-toy).
|
||||
|
||||
We invite you to experiment beyond the [try.sh](%%REPO_URL%%/2024/endoh2/try.sh), and test with these "_body.txt_" files:
|
||||
|
||||
* bottle.txt
|
||||
* cylinder.txt
|
||||
* egg.txt
|
||||
* halo.txt
|
||||
* stick.txt
|
||||
* tippe-top.txt
|
||||
* tippe-top2.txt
|
||||
* tippe-top3.txt
|
||||
* top.txt
|
||||
* top2.txt
|
||||
* top3.txt
|
||||
* top4.txt
|
||||
* umbrella.txt
|
||||
* vase.txt
|
||||
|
||||
For example:
|
||||
|
||||
``` <!---sh-->
|
||||
./prog < vase.txt
|
||||
```
|
||||
|
||||
Moreover, you should experiment with various simulation parameters. On the make line you may set:
|
||||
|
||||
```
|
||||
| Perameter | Default | Meaning
|
||||
|-------------|-----------------------------------------------------|
|
||||
| WIDTH | 120 | Screen width |
|
||||
| | | |
|
||||
| HEIGHT | 24 | Screen height |
|
||||
| | | |
|
||||
| TIMESTEP | 0.01 | Simulation time step |
|
||||
| | | a smaller dt |
|
||||
| | | increases precision |
|
||||
| | | down the simulation |
|
||||
| | | |
|
||||
| RESTITUTION | 0.5 | Coefficient of restitution |
|
||||
| | | |
|
||||
| FRICTION | 0.5 | Coefficient of friction |
|
||||
| | | |
|
||||
| RPM | 750 | Initial rotation speed in RPM |
|
||||
| | | |
|
||||
| FASTRPM | 4000 | Tipple top initial rotation speed in RPM |
|
||||
| | | used by ./tipple, not ./prog |
|
||||
| | | |
|
||||
| TILT | 5 | Initial tilt angle |
|
||||
| | | in degrees |
|
||||
| | | 0 is upright |
|
||||
| | | positive values tilt to the right |
|
||||
```
|
||||
|
||||
For example, to increase the "_Coefficient of friction_" to **0.75**,
|
||||
the "_Initial rotation speed in RPM_" to **600**, and the "_Initial
|
||||
tilt angle_" to **15**:
|
||||
|
||||
``` <!---sh-->
|
||||
make clobber all FRICTION=0.75 RPM=600 TILT=15
|
||||
|
||||
./prog < top.txt
|
||||
```
|
||||
|
||||
Now we would like to see if this entry can be hacked to demonstrate the
|
||||
[Dzhanibekov effect](https://en.wikipedia.org/wiki/Tennis_racket_theorem).
|
||||
|
||||
|
||||
## Author's remarks:
|
||||
|
||||
|
||||
### A Spinning Top Simulator
|
||||
|
||||
```
|
||||
@@
|
||||
@@
|
||||
@@@@@@@@@@@@
|
||||
@@ @@@@@@@@@@@@@@@@
|
||||
@@@@ @@@@@@@@@@@@@@@@
|
||||
@@@@@@@ @@@@@@@@@@@ @
|
||||
@@@@@@@@@@@ @@@
|
||||
@@@@@@@@@@@@@@@@@@@@@@@@
|
||||
@@@@@@@@@@@@@@@@@@@@@@@@
|
||||
@@@@@@@@@@@@@@@@@@@@@
|
||||
@@@@@@@@@@@@@@@@@@@@
|
||||
@@@@@@@@@@@@@@@@
|
||||
@@@@@@@@@@@@@
|
||||
@@@@@@@@@
|
||||
@@@@
|
||||
@@
|
||||
@@
|
||||
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
|
||||
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
|
||||
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
|
||||
```
|
||||
|
||||
This is a physics engine that simulates the motion of a rotating rigid body, such as a [top](https://en.wikipedia.org/wiki/Top).
|
||||
|
||||
|
||||
#### How to run
|
||||
|
||||
Compilation requires specifying several `-D` options:
|
||||
|
||||
```
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=1000 -Dtilt=5 -o prog prog.c
|
||||
```
|
||||
|
||||
These options define the following parameters:
|
||||
|
||||
* `-DW=120`: Screen width.
|
||||
* `-DH=24`: Screen height.
|
||||
* `-Ddt=0.01`: Simulation time step (a smaller `dt` increases precision but slows down the simulation).
|
||||
* `-De=0.5`: Coefficient of restitution.
|
||||
* `-Du=0.5`: Coefficient of friction.
|
||||
* `-Drpm=1000`: Initial rotation speed (in RPM).
|
||||
* `-Dtilt=5`: Initial tilt angle (in degrees; 0 is upright; positive values tilt to the right).
|
||||
|
||||
Then, run the program like this:
|
||||
|
||||
```
|
||||
$ ./prog < top.txt
|
||||
```
|
||||
|
||||
|
||||
#### Input file format
|
||||
|
||||
The input file defines the shape of a rigid body. Here's an example:
|
||||
|
||||
```
|
||||
// A typical spinning top
|
||||
|
||||
// Use `-Drpm=1000 -Dtilt=5`
|
||||
|
||||
.
|
||||
.
|
||||
. // Twirl here
|
||||
.
|
||||
.
|
||||
.
|
||||
...
|
||||
#####
|
||||
##
|
||||
# // Spin!
|
||||
##
|
||||
#####
|
||||
..
|
||||
.
|
||||
.
|
||||
. // Looks painful
|
||||
```
|
||||
|
||||
This figure is rotated around its left edge to create a 3D object (a solid of revolution).
|
||||
Only solids of revolution are supported by this simulator.
|
||||
|
||||
Internally, the rigid body is modeled as a collection of particles (point masses). Each character in the input file has the following meaning:
|
||||
|
||||
* A full-stop (or any printable character whose LSB is 0): Represents light particle.
|
||||
* A hash (or any character whose LSB is 1): Represents heavy particle.
|
||||
* A space: Represents no particle (empty space).
|
||||
* A slash: Indicates the start of a comment; everything after it on the line is ignored.
|
||||
|
||||
|
||||
#### Algorithm overview
|
||||
|
||||
The core algorithm works as follows:
|
||||
|
||||
1. Compute the inertia tensor
|
||||
2. Compute an inverse of the tensor
|
||||
3. For each particle in contact with the floor:
|
||||
3-1. Compute the normal force
|
||||
3-2. Compute friction
|
||||
3-3. Convert these into the resultant force and torque acting on the body's center of mass
|
||||
4. Update the position, velocity, angular velocity, and orientation of the body
|
||||
|
||||
For the detailed theory, refer to a physics textbook.
|
||||
|
||||
To keep code size minimal, this simulator uses [quaternions](https://en.wikipedia.org/wiki/Quaternion) to represent 3D vectors and matrices.
|
||||
Quaternion multiplication is powerful, allowing the inertia tensor and its inverse to be calculated concisely, each requiring only about 100 characters of code.
|
||||
Because `math.h` doesn't natively support quaternions for these operations, it's not used at all. This also means linking with `-lm` is unnecessary.
|
||||
|
||||
Motion blur is used in the rendering. You can observe it more clearly by pausing the animation (e.g., with Ctrl+S in some terminals).
|
||||
|
||||
Distant points appear as colons (`:`), while closer ones appear as at-signs (`@`).
|
||||
|
||||
|
||||
#### Included data
|
||||
|
||||
A few shape files are provided. The top*.txt files are standard spinning top shapes.
|
||||
|
||||
```
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=1000 -Dtilt=5 -o prog prog.c && ./prog < top.txt
|
||||
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=500 -Dtilt=5 -o prog prog.c && ./prog < top2.txt
|
||||
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=500 -Dtilt=5 -o prog prog.c && ./prog < top3.txt
|
||||
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=500 -Dtilt=5 -o prog prog.c && ./prog < top4.txt
|
||||
```
|
||||
|
||||
The [tippe top](https://en.wikipedia.org/wiki/Tippe_top) is a top that flips itself over when spun quickly.
|
||||
|
||||
```
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=2200 -Dtilt=5 -o prog prog.c && ./prog < tippe-top.txt
|
||||
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=4000 -Dtilt=5 -o prog prog.c && ./prog < tippe-top2.txt
|
||||
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=4000 -Dtilt=5 -o prog prog.c && ./prog < tippe-top3.txt
|
||||
```
|
||||
|
||||
Spinning a boiled egg? Try this with `-Dtilt=90` to start it from a lying position.
|
||||
|
||||
```
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=1300 -Dtilt=90 -o prog prog.c && ./prog < egg.txt
|
||||
```
|
||||
|
||||
Spin everyday items -- no risk of breaking them:
|
||||
|
||||
```
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=1000 -Dtilt=175 -o prog prog.c && ./prog < bottle.txt
|
||||
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=1000 -Dtilt=5 -o prog prog.c && ./prog < bottle.txt
|
||||
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=1000 -Dtilt=5 -o prog prog.c && ./prog < umbrella.txt
|
||||
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=2000 -Dtilt=5 -o prog prog.c && ./prog < vase.txt
|
||||
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=2000 -Dtilt=20 -o prog prog.c && ./prog < vase.txt
|
||||
```
|
||||
|
||||
More shapes: `stick.txt`, `cylinder.txt`, `halo.txt`, and even `prog.c`.
|
||||
|
||||
Yes, `prog.c` itself can be used as input. Try it:
|
||||
|
||||
```
|
||||
$ gcc -O3 -DW=120 -DH=24 -Ddt=0.01 -De=0.5 -Du=0.5 -Drpm=1000 -Dtilt=5 -o prog prog.c && ./prog < prog.c
|
||||
```
|
||||
|
||||
|
||||
<!--
|
||||
|
||||
Copyright © 1984-2025 by Landon Curt Noll and Leonid A. Broukhis. All Rights Reserved.
|
||||
|
||||
You are free to share and adapt this file under the terms of this license:
|
||||
|
||||
Creative Commons Attribution-ShareAlike 4.0 International (CC BY-SA 4.0)
|
||||
|
||||
For more information, see:
|
||||
|
||||
https://creativecommons.org/licenses/by-sa/4.0/
|
||||
|
||||
-->
|
||||
Reference in new issue
Block a user