Skip to content

Instantly share code, notes, and snippets.

View wchargin's full-sized avatar

Willow Chargin wchargin

View GitHub Profile
<!doctype html>
<div id="root"></div>
<script type="module">
import React, { useEffect, useState } from "https://esm.sh/[email protected]";
import ReactDOM from "https://esm.sh/[email protected]";
import { animated, useSpring } from "https://esm.sh/@react-spring/[email protected]";
import { usePrevious } from "https://esm.sh/@uidotdev/[email protected]";
import * as turf from "@turf/turf"; // v7.0.0
const coords = (pointFeature) => pointFeature.geometry.coordinates;
const pointToLineDistanceOptions = { method: "geodesic" };
// ^ setting "planar" doesn't change things substantively
let maxError = -Infinity;
let argmaxError;
let nErrorOverOnePercent = 0;
{
"target": {
"type": "Feature",
"properties": {},
"geometry": {
"type": "Point",
"coordinates": [
11.991689565382663,
34.00578044047174
]
# Create GeoJSON `Feature` values
def feature: {type: "Feature", properties: {}, geometry: .};
# Create GeoJSON `Geometry` values
def geometry($type): {$type, geometry: .};
def point: geometry("Point");
def multipoint: geometry("MultiPoint");
def linestring: geometry("LineString");
def multilinestring: geometry("MultiLineString");
def polygon: geometry("Polygon");
@wchargin
wchargin / index.html
Created July 27, 2024 17:35
useStable with quick-exit
<!doctype html>
<div id="root" />
<script type="module">
import React, {
createElement as h,
useState,
} from "https://esm.sh/react@18?dev";
import { createRoot } from "https://esm.sh/react-dom@18/client?dev";
const lazyEq = (a, b) => JSON.stringify(a) === JSON.stringify(b);
@wchargin
wchargin / pan.js
Created July 2, 2024 22:38
bookmarklets for audio manipulation (speed and panning)
javascript:((pan) => { if (!window.__wcharginPanState) { const ctx = new AudioContext(); const panner = new StereoPannerNode(ctx); panner.connect(ctx.destination); const vsrcSymbol = Symbol("mediaSourceOutput"); window.__wcharginPanState = { ctx, panner, vsrcSymbol };}; const {ctx, panner, vsrcSymbol} = window.__wcharginPanState; for (const video of document.querySelectorAll("video")) { if (!video[vsrcSymbol]) { video[vsrcSymbol] = ctx.createMediaElementSource(video); video[vsrcSymbol].connect(panner); } } panner.pan.value = pan; })(Number(prompt("pan? (-1 to 1)")));
@wchargin
wchargin / cmp.js
Created February 5, 2024 23:07
sortAsciinumeric, extractNumbers: numeric-aware string sorting
/**
* A comparator that follows elements' natural ordering. Useful for comparing
* numbers: `[8, 9, 10].sort()` is broken, but `[8, 9, 10].sort(natural)` works
* as expected. Also useful as a "neutral" comparator to give to combinators.
*/
function natural(a, b) {
if (a > b) return 1;
if (a < b) return -1;
return 0;
}
@wchargin
wchargin / chances.dat
Last active October 30, 2023 00:21
plot backpack battles item chances
round common rare epic legend godly
1 90 10 0 0 0
2 84 15 1 0 0
3 75 20 5 0 0
4 64 25 10 1 0
5 45 35 15 5 0
6 29 40 20 10 1
7 20 35 25 15 5
8 20 30 25 15 10
9 20 28 25 15 12
@wchargin
wchargin / Caddyfile
Last active October 29, 2023 06:07
Caddy x GCS reverse proxy via storage.googleapis.com
# requires caddyserver/cache-handler module
{
order cache before rewrite
cache
log default {
output stdout
# http.handlers.cache logs the entire contents of request
# bodies at info level(??!)
exclude http.handlers.cache
@wchargin
wchargin / art.rs.patch
Created October 11, 2023 20:16
dump flow fields before and after disturbances
diff --git a/src/art.rs b/src/art.rs
index bcba7e0..1d99457 100644
--- a/src/art.rs
+++ b/src/art.rs
@@ -548,10 +548,84 @@ impl FlowField {
} => Self::raw_circular(*circularity, *direction, *rotation, traits.version, rng),
};
let disturbances = Disturbance::build(traits, rng);
+ ff.dump(&[], "flowfield0_initial.png").unwrap();
+ ff.dump(&disturbances, "flowfield1_disturbances.png")