Mirai's Miscellaneous Misadventures

M51 / core / controls.c

1/* license: AGPLv3 or later */
2/* copyright 2024 zamfofex */
3
4#include <mimimi.h>
5
6void mimimi_history_tick(struct mimimi_history *history, unsigned char left, unsigned char right)
7{
8	history->left <<= 1;
9	history->right <<= 1;
10	
11	history->left &= 0xFFFF;
12	history->right &= 0xFFFF;
13	
14	if (left != 0) history->left |= 1;
15	if (right != 0) history->right |= 1;
16}
17
18static int mimimi_count_oscillations(unsigned int history)
19{
20	int count, i;
21	unsigned char prev;
22	
23	count = 0;
24	prev = history & 1;
25	for (i = 0 ; i < 16 ; i++)
26	{
27		if ((history & 1) != prev) count++;
28		prev = history & 1;
29		history >>= 1;
30	}
31	
32	return count;
33}
34
35void mimimi_controls_tick(struct mimimi_walk *walk, struct mimimi_history *history, void (*jump)(void *data), void *data)
36{
37	int left_oscillations, right_oscillations;
38	
39	left_oscillations = mimimi_count_oscillations(history->left);
40	right_oscillations = mimimi_count_oscillations(history->right);
41	
42	switch (walk->direction)
43	{
44	case 0:
45		if ((history->right & 1) != 0)
46		{
47			walk->direction = 2;
48			if (right_oscillations > 1 && (history->right&2) == 0)
49				(*jump)(data);
50		}
51		if ((history->left & 1) != 0)
52		{
53			walk->direction = 1;
54			if (left_oscillations > 1 && (history->left&2) == 0)
55				(*jump)(data);
56		}
57		break;
58	case 1:
59		if ((history->left & 1) == 0) walk->direction = 0;
60		break;
61	case 2:
62		if ((history->right & 1) == 0) walk->direction = 0;
63		break;
64	}
65}