summaryrefslogtreecommitdiff
path: root/api/canvas
diff options
context:
space:
mode:
Diffstat (limited to 'api/canvas')
-rw-r--r--api/canvas/canvas.go33
-rw-r--r--api/canvas/canvas_test.go2
2 files changed, 15 insertions, 20 deletions
diff --git a/api/canvas/canvas.go b/api/canvas/canvas.go
index 717d924..d44dd87 100644
--- a/api/canvas/canvas.go
+++ b/api/canvas/canvas.go
@@ -1,14 +1,13 @@
-// Package canvas is a single shared r/place-style grid. The append-only pixel
-// log in the database is the source of truth; periodic binary snapshots let a
-// new client load the current state without replaying all of history.
package canvas
import (
+ "compress/gzip"
"database/sql"
"encoding/json"
"fmt"
"log"
"net/http"
+ "strings"
"time"
"github.com/gorilla/websocket"
@@ -18,12 +17,12 @@ import (
)
const (
- Rows = 64
- Cols = 64
+ Rows = 512
+ Cols = 512
Scale = 8
- placeCooldown = 2 * time.Second
- snapshotThreshold = 50
+ placeCooldown = 500 * time.Millisecond
+ snapshotThreshold = 500
defaultColor = 0xffffff
writeWait = 10 * time.Second
@@ -32,7 +31,6 @@ const (
maxMessageSize = 256
)
-// r/place 2017 palette.
var palette = []int{
0xffffff, 0xe4e4e4, 0x888888, 0x222222,
0xffa7d1, 0xe50000, 0xe59500, 0xa06a42,
@@ -61,8 +59,6 @@ type outbound struct {
Ms int64 `json:"ms,omitempty"`
}
-// ---- snapshot / state ------------------------------------------------------
-
func blankCanvas() []byte {
buf := make([]byte, Rows*Cols*3)
for i := 0; i < len(buf); i += 3 {
@@ -83,7 +79,6 @@ func setPixel(buf []byte, x, y, color int) {
buf[i+2] = byte(color)
}
-// baseline returns the latest snapshot's bytes and through-id, or a blank canvas.
func baseline(db *sql.DB) ([]byte, int64, error) {
snap, err := database.LatestCanvasSnapshot(db)
if err != nil {
@@ -138,8 +133,6 @@ func takeSnapshot(db *sql.DB) error {
return database.DeleteOldCanvasSnapshots(db)
}
-// ---- hub -------------------------------------------------------------------
-
type Hub struct {
db *sql.DB
clients map[*Client]bool
@@ -246,8 +239,6 @@ func (h *Hub) handlePlace(p placement) {
}
}
-// ---- client ----------------------------------------------------------------
-
type Client struct {
hub *Hub
conn *websocket.Conn
@@ -308,8 +299,6 @@ func (c *Client) writePump() {
}
}
-// ---- continuations ---------------------------------------------------------
-
type pageConfig struct {
Rows int
Cols int
@@ -348,7 +337,15 @@ func StateContinuation(context *types.RequestContext, req *http.Request, resp ht
return success(context, req, resp)
}
resp.Header().Set("Content-Type", "application/octet-stream")
- resp.Write(buf)
+ // mostly-blank canvas, so it gzips down to almost nothing.
+ if strings.Contains(req.Header.Get("Accept-Encoding"), "gzip") {
+ resp.Header().Set("Content-Encoding", "gzip")
+ gz := gzip.NewWriter(resp)
+ defer gz.Close()
+ gz.Write(buf)
+ } else {
+ resp.Write(buf)
+ }
return success(context, req, resp)
}
}
diff --git a/api/canvas/canvas_test.go b/api/canvas/canvas_test.go
index 324a3a1..38bb492 100644
--- a/api/canvas/canvas_test.go
+++ b/api/canvas/canvas_test.go
@@ -53,7 +53,6 @@ func TestSnapshotBakesThenReplays(t *testing.T) {
if err := takeSnapshot(db); err != nil {
t.Fatal(err)
}
- // a placement after the snapshot must be replayed on top of it
if _, err := database.SavePixel(db, "u", 6, 6, 0x02be01); err != nil {
t.Fatal(err)
}
@@ -69,7 +68,6 @@ func TestSnapshotBakesThenReplays(t *testing.T) {
t.Errorf("replayed pixel = %06x, want green", got)
}
- // snapshots are kept to one row
if err := takeSnapshot(db); err != nil {
t.Fatal(err)
}