diff --git a/.gitignore b/.gitignore index afb47ad..7f62b1f 100644 --- a/.gitignore +++ b/.gitignore @@ -11,3 +11,4 @@ image.png logs.txt rgb111-full.png state-new.json +settings.json diff --git a/async-bot.py b/async-bot.py index 08c06c3..4b76a23 100644 --- a/async-bot.py +++ b/async-bot.py @@ -3,7 +3,7 @@ import asyncio from typing import Optional from socketio import AsyncSimpleClient from aiohttp import ClientSession -from aiohttp_proxy import ProxyConnector +from aiohttp_socks import ProxyConnector from PIL import Image, ImageFont, ImageDraw, ImageFilter from base64 import b64decode from random import choice @@ -68,7 +68,7 @@ class AsyncBotManager: else: print("unknown event", event, data) - async def writer(self, proxy_url: Optional[str] = None): + async def writer(self, bot_index: int, proxy_url: Optional[str] = None): proxy = ProxyConnector.from_url(proxy_url) if proxy_url else None async with ClientSession(connector=proxy) as http: async with AsyncSimpleClient(http_session=http) as sio: @@ -77,14 +77,14 @@ class AsyncBotManager: try: event, data = await sio.receive(0.1) if event not in ("full_state", "batched_bit_toggles"): - print("!!!", event, data) + print(bot_index, "!!!", event, data) except Exception: pass index, target = choice(list(self.difference.items())) y, x = divmod(index, 1000) curr = self.canvas.getpixel((x, y)) > 0 # type: ignore if curr != target: - print("swap", x, y, index) + print(bot_index, "swap", x, y) await sio.emit("toggle_bit", { "index": index }) @@ -124,14 +124,27 @@ async def amain(): mgr.difference[ndx_start] = r > 128 mgr.difference[ndx_start + 1] = g > 128 mgr.difference[ndx_start + 2] = b > 128 + elif elem["type"] == "rgb565": + ox, oy = elem["x"], elem["y"] + with Image.open(elem["path"]).convert("RGB") as im: + for y in range(im.height): + for x in range(im.width): + r, g, b = im.getpixel((x, y)) # type: ignore + ndx_start: int = (x + ox + (y + oy) * 250) * 16 + color = (r >> 3) << 13 + color |= (g >> 2) << 5 + color |= (b >> 3) + + for i in range(16): + mgr.difference[ndx_start + i] = ((color >> i) & 1) > 0 if (n_proxies := len(settings["proxies"])): await asyncio.gather(*[ - mgr.writer(settings["proxies"][i % n_proxies]) for i in range(settings["n_bots"]) + mgr.writer(i, settings["proxies"][i % n_proxies]) for i in range(settings["n_bots"]) ], return_exceptions=True) else: await asyncio.gather(*[ - mgr.writer() for _ in range(settings["n_bots"]) + mgr.writer(i) for i in range(settings["n_bots"]) ], return_exceptions=True) diff --git a/casey565.png b/casey565.png new file mode 100644 index 0000000..c380ea3 Binary files /dev/null and b/casey565.png differ diff --git a/stream.py b/stream.py new file mode 100644 index 0000000..3692ba0 --- /dev/null +++ b/stream.py @@ -0,0 +1,36 @@ + +from base64 import b64decode +from socketio import SimpleClient +from requests import get +from sys import stdout + + +BASE_URL = "https://onemillioncheckboxes.com" + + +canvas = bytearray(1000000) + +with get(f"{BASE_URL}/api/initial-state") as req: + data = req.json() + buffer = b64decode(data["full_state"].encode() + b"=") + canvas[:] = buffer + + +with SimpleClient() as sio: + sio.connect(f"{BASE_URL}/socket.io") + while True: + name, data = sio.receive() + if name == "batched_bit_toggles": + bits_on, bits_off, timestamp = data + for ndx in bits_on: + byte, bit = divmod(ndx, 8) + canvas[byte] |= (1 << bit) + for ndx in bits_off: + byte, bit = divmod(ndx, 8) + canvas[byte] &= 0xFF ^ (1 << bit) + elif name == "full_state": + buffer = b64decode(data["full_state"].encode() + b"=") + canvas[:] = buffer + + stdout.buffer.write(canvas) + stdout.buffer.flush()