shithub: gm4s

Download patch

ref: 861520c581d13762bcd2f9d9a08e8b69a0af30a9
parent: dedb6f71a08333b6a06ee22ea654cbe95ce27b08
author: qwx <qwx@sciops.net>
date: Sat Mar 15 21:13:39 EDT 2025

draw extra space for "ui" elements, show hold and next pieces

--- a/dat.h
+++ b/dat.h
@@ -38,8 +38,11 @@
 	Ncol = 10,
 	Block = 16,
 
-	Wwidth = Block * Ncol,
-	Wheight = Block * (Nstartrow + Nextrarows),
+	Wwidth = Ncol,
+	Wheight = Nstartrow + Nextrarows,
+	Wside = 3,
+	Vwidth = Block * (Wwidth + 2 * Wside),
+	Vheight = Block * Wheight,
 
 	K← = 1<<0,
 	K→ = 1<<1,
@@ -55,6 +58,8 @@
 };
 #define T0	(double)BILLION / Tspeed0
 extern char playfield[Ncol * Nrow];
+extern int held;
+extern int hist[4];
 extern double T;
 
 enum{
--- a/game.c
+++ b/game.c
@@ -4,8 +4,12 @@
 #include "fns.h"
 #include "/sys/src/games/eui.h"
 
+/* FIXME: grace period before freeze */
+
 char playfield[Ncol * Nrow];
 Current *cur;
+int held = -1;
+int hist[4] = {FZ, FZ, FS, FS};
 
 enum{
 	Nlineperlvl = 10,
@@ -12,7 +16,6 @@
 	Timeinc = BILLION / 10.0,
 };
 static vlong ncleared;
-static int held = -1;
 
 static int bfield[Nrow];
 
@@ -31,7 +34,6 @@
 getpiece(void)
 {
 	int i, *h, r;
-	static int hist[4] = {FZ, FZ, FS, FS};
 
 	for(r=i=0; i<5; i++){
 		r = trand() % 7;
--- a/gm4s.c
+++ b/gm4s.c
@@ -127,8 +127,7 @@
 	|| (evc = chancreate(sizeof(ulong), 0)) == nil
 	|| (keychan = chancreate(sizeof(ulong), 8)) == nil)
 		sysfatal("chancreate: %r");
-	/* FIXME: simultaneous kproc and joyproc in eui */
-	initemu(Wwidth, Wheight, 4, XRGB32, 1, nil);
+	initemu(Vwidth, Vheight, 4, XRGB32, 1, nil);
 	initimg();
 	fmtinstall('H', encodefmt);
 	regkey("up", Kup, K↑);
--- a/piece.c
+++ b/piece.c
@@ -7,6 +7,7 @@
 #include "fns.h"
 #include "/sys/src/games/eui.h"
 
+/* FIXME: stabler rotations? */
 int fours[NF][Nrot] = {
 	[FI] {
 		0b0000111100000000,
@@ -63,20 +64,18 @@
 };
 static Image *piece[NF];
 
-enum{
-	Nline = Ncol * Block,
-};
+/* FIXME: draw level, line clears, score */
+/* FIXME: freeze screen on game over + print message instead of immediate exit */
 
 static void
 drawplayfield(void)
 {
-	int w;
 	u32int c, *s, *p, *pe;
 	char fc, *f, *fe;
 
-	w = Block * 1;
-	p = (u32int *)pic;
-	f = playfield + Ncol * (Nrow - Nstartrow - Nextrarows);
+	memset(pic, 0, Vwidth * Vheight * sizeof *p);	/* FIXME: sides */
+	p = (u32int *)pic + Wside * Block;
+	f = playfield + Wwidth * (Nrow - Wheight);
 	for(s=p, fe=playfield+nelem(playfield); f<fe; f++){
 		if((fc = *f) == 0)
 			//c = cols[nrand(nelem(cols))];
@@ -83,10 +82,10 @@
 			c = 0xff000000;
 		else
 			c = cols[fc - 1];
-		for(pe=p+w; p<pe; p++)
+		for(pe=p+Block; p<pe; p++)
 			*p = c;
-		if(p - s == Ncol * w){
-			p += Ncol * w * (Block - 1);
+		if(p - s == Wwidth * Block){
+			p += Vwidth * (Block - 1) + 2 * Wside * Block;
 			s = p;
 		}
 	}
@@ -93,40 +92,56 @@
 }
 
 static void
-drawpiece(void)
+drawfour(int x, int y, int rot, int type)
 {
-	int f, x, n, w;
+	int f, m, n;
 	u32int c, *l, *s, *p, *pe;
 
-	if(cur == nil)
-		return;
 	s = (u32int *)pic;
-	s += (cur->y - Nstartrow + Nextrarows) * Nline * Block + cur->x * Block;
+	s += (y - Nstartrow + Nextrarows) * Vwidth * Block + x * Block;
 	l = s;
-	c = cols[cur->type];
-	f = fours[cur->type][cur->rot];
-	w = Block * 1;
-	for(n=0, x=1<<(Nside*Nside-1); x>0; x>>=1){
-		if(s >= (u32int *)pic && f & x)
-			for(p=s, pe=p+w; p<pe; p++)
+	c = cols[type];
+	f = fours[type][rot];
+	for(n=0, m=1<<(Nside*Nside-1); m>0; m>>=1){
+		if(s >= (u32int *)pic && f & m)
+			for(p=s, pe=p+Block; p<pe; p++)
 				*p = c;
 		if(++n == Nside){
-			l += Block * Ncol * w;
+			l += Vwidth * Block;
 			s = l;
 			n = 0;
 		}else
-			s += w;
+			s += Block;
 	}
 }
 
 static void
+drawui(void)
+{
+	int y, *h;
+
+	if(held != -1)
+		drawfour(-1, Nrow / 2, 1, held);
+	for(y=1, h=hist+1; h<hist+nelem(hist); h++, y+=5)
+		drawfour(Wside + Wwidth, Nstartrow - Nextrarows + y, 1, *h);
+}
+
+static void
+drawpiece(void)
+{
+	if(cur == nil)
+		return;
+	drawfour(Wside + cur->x, cur->y, cur->rot, cur->type);
+}
+
+static void
 vscalepic(void)
 {
 	int n;
 	u32int *p, *s, *e;
 
-	n = 1 * Ncol * Block;
-	for(s=(u32int*)pic, e=s+n*Wheight; s<e; s=p)
+	n = Vwidth;
+	for(s=(u32int*)pic, e=s+n*Vheight; s<e; s=p)
 		for(p=s+n; p<s+n*Block; p+=n)
 			memcpy(p, s, n * sizeof *p);
 }
@@ -136,6 +151,7 @@
 {
 	drawplayfield();
 	drawpiece();
+	drawui();
 	vscalepic();
 	flushmouse(1);
 	flushscreen();
--