First "Hello MacLO" build

* Added base "Hello MacLO" app
* Added first attempt at porting game engine from [ArduLO](https://github.com/jonthysell/ArduLO)
* Added README.md and LICENSE.md
This commit is contained in:
Jon Thysell 2021-10-11 11:04:12 -07:00
parent 266a8ddc32
commit 1f51e4e4d2
14 changed files with 14 additions and 2 deletions

5
.gitattributes vendored
View File

@ -1,4 +1,5 @@
* text=auto
*.c text eol=LF
*.h text eol=LF
*.c text eol=CRLF
*.h text eol=CRLF
*.md text eol=CRLF

1
LICENSE.md Normal file
View File

@ -0,0 +1 @@
MIT License Copyright (c) 2021 Jon Thysell Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

1
README.md Normal file
View File

@ -0,0 +1 @@
# MacLO # MacLO is a clone of the puzzle game [Lights Out](https://en.wikipedia.org/wiki/Lights_Out_(game)) for the Classic Macintosh. ## Build ## To build MacLO from source, you'll need a working THINK C 5.0 development environment. ## Play ## MacLO contains two sets of 50 puzzles. The objective is to turn off all of the lights in as few moves as possible. Clicking a light will cause it and the nearby lights to toggle in the shape of a plus. After finshing a puzzle, you'll be given a score in one to three stars. Here you can either move on to the next puzzle or retry for a better score. Try to get three stars on all 50 levels in the set! ## Errata ## MacLO is open-source under the MIT license. Copyright (c) 2021 Jon Thysell

1
src/Common.c Normal file
View File

@ -0,0 +1 @@
// Copyright (c) Jon Thysell <http://jonthysell.com> // Licensed under the MIT License. #include "Common.h" WindowPtr MainWindow;

1
src/Common.h Normal file
View File

@ -0,0 +1 @@
// Copyright (c) Jon Thysell <http://jonthysell.com> // Licensed under the MIT License. #ifndef COMMON_H #define COMMON_H #include "stdbool.h" #include "stdint.h" #define min(a,b) ((a)<(b)?(a):(b)) #define max(a,b) ((a)>(b)?(a):(b)) #define bitRead(value, bit) (((value) >> (bit)) & 0x01) #define bitSet(value, bit) ((value) |= (1UL << (bit))) #define bitClear(value, bit) ((value) &= ~(1UL << (bit))) #define bitToggle(value, bit) ((value) ^= (1UL << (bit))) #define bitWrite(value, bit, bitValue) ((bitBalue) ? bitSet(value, bit) : bitClear(value, bit)) extern WindowPtr MainWindow; #endif

1
src/GameEngine.c Normal file
View File

@ -0,0 +1 @@
// Copyright (c) Jon Thysell <http://jonthysell.com> // Licensed under the MIT License. #include "Common.h" #include "GameEngine.h" const int8_t PuzzleSize = 5; const uint8_t MaxStars = 3; const uint8_t MaxHalfStars = 6; const uint8_t MinHalfStars = 1; const uint16_t PerfectScore = 300; // LevelCount * MaxHalfStars void GameEngine_LoadLevel(GameEngine *engine, const int8_t level, const bool setB) { engine->Level = Levels_BoundLevel(level); engine->Lights = Levels_GetLightsForLevel(engine->Level, setB); engine->Par = Levels_GetParForLevel(engine->Level); engine->Moves = 0; } bool GameEngine_GetLight(const GameEngine *engine, const int8_t x, const int8_t y) { if (x >= 0 && x < PuzzleSize && y >= 0 && y < PuzzleSize) { return bitRead(engine->Lights, y * PuzzleSize + x); } return false; } bool GameEngine_IsCompleted(const GameEngine *engine) { return engine->Lights == 0; } uint8_t GameEngine_GetHalfStars(const GameEngine *engine) { uint8_t halfStarsLost = engine->Moves <= engine->Par ? 0 : max(0, (1 + engine->Moves - engine->Par) / 2); return max(MinHalfStars, MaxHalfStars - halfStarsLost); } void GameEngine_ToggleSingleLight(GameEngine *engine, const int8_t x, const int8_t y) { if (x >= 0 && x < PuzzleSize && y >= 0 && y < PuzzleSize) { bitToggle(engine->Lights, y * PuzzleSize + x); } } void GameEngine_ToggleLights(GameEngine *engine, const int8_t x, const int8_t y) { int8_t targetX = max(0, min(x, PuzzleSize - 1)); int8_t targetY = max(0, min(y, PuzzleSize - 1)); GameEngine_ToggleSingleLight(engine, targetX, targetY); GameEngine_ToggleSingleLight(engine, targetX + 1, targetY); GameEngine_ToggleSingleLight(engine, targetX, targetY + 1); GameEngine_ToggleSingleLight(engine, targetX - 1, targetY); GameEngine_ToggleSingleLight(engine, targetX, targetY - 1); engine->Moves++; }

1
src/GameEngine.h Normal file
View File

@ -0,0 +1 @@
// Copyright (c) Jon Thysell <http://jonthysell.com> // Licensed under the MIT License. #ifndef GAMEENGINE_H #define GAMEENGINE_H #include "Levels.h" extern const int8_t PuzzleSize; extern const uint8_t MaxStars; extern const uint8_t MaxHalfStars; extern const uint8_t MinHalfStars; extern const uint16_t PerfectScore; typedef struct GameEngine { int8_t Level; uint32_t Lights; uint16_t Par; uint16_t Moves; } GameEngine; void GameEngine_LoadLevel(GameEngine *engine, const int8_t level, const bool setB); bool GameEngine_GetLight(const GameEngine *engine, const int8_t x, const int8_t y); bool GameEngine_IsCompleted(const GameEngine *engine); uint8_t GameEngine_GetHalfStars(const GameEngine *engine); void GameEngine_ToggleLights(GameEngine *engine, const int8_t x, const int8_t y); #endif

1
src/Levels.c Normal file
View File

@ -0,0 +1 @@
// Copyright (c) Jon Thysell <http://jonthysell.com> // Licensed under the MIT License. #include "Common.h" #include "Levels.h" const int8_t LevelCount = 50; const uint32_t Levels_LightsA[] = { 0x0005400UL, 0x15A82B5UL, 0x0ADEF6AUL, 0x1B88360UL, 0x1BC5EEFUL, 0x0EAD400UL, 0x0F8C62FUL, 0x0AAA880UL, 0x07D3BEAUL, 0x00039CEUL, 0x0EAD6B5UL, 0x0A76D5FUL, 0x022AA88UL, 0x0210800UL, 0x0010040UL, 0x1F08421UL, 0x1F71000UL, 0x0455544UL, 0x1505415UL, 0x0004400UL, 0x021385EUL, 0x0E8C62EUL, 0x0467000UL, 0x12FC400UL, 0x1E79C61UL, 0x118FE31UL, 0x04211C4UL, 0x1CE7000UL, 0x0000040UL, 0x0001000UL, 0x11CD671UL, 0x1F1111FUL, 0x198D508UL, 0x1EB4634UL, 0x00AC558UL, 0x11FC544UL, 0x00739C0UL, 0x1555555UL, 0x0A60C2AUL, 0x0002800UL, 0x0421151UL, 0x0749D27UL, 0x0E11D71UL, 0x0E27F60UL, 0x157F0AEUL, 0x0477DC4UL, 0x10917E4UL, 0x0089220UL, 0x1151151UL, 0x1FFFFFFUL, }; const uint32_t Levels_LightsB[] = { 0x1B06C1BUL, 0x1F2009FUL, 0x1F5115FUL, 0x11D822AUL, 0x0466CC4UL, 0x0AFD7EAUL, 0x158EE35UL, 0x0013800UL, 0x0531110UL, 0x11AC6A0UL, 0x1F739DFUL, 0x1150151UL, 0x0E4394EUL, 0x093BD2FUL, 0x0EAD6B5UL, 0x0E4384EUL, 0x1F8D63FUL, 0x1505415UL, 0x0AABAAAUL, 0x1500015UL, 0x1FBEFBFUL, 0x118FC9FUL, 0x1B56D5BUL, 0x1F8FD44UL, 0x118D771UL, 0x1FAFEBFUL, 0x0E2108EUL, 0x1B77D4EUL, 0x0001000UL, 0x1101011UL, 0x1BD837BUL, 0x047440AUL, 0x1576DD5UL, 0x11CD671UL, 0x15AEEB5UL, 0x15AB884UL, 0x1FAD6B5UL, 0x00739C0UL, 0x11FC544UL, 0x1555555UL, 0x11729D1UL, 0x0454544UL, 0x1502815UL, 0x0AFABEAUL, 0x1FEFEBFUL, 0x1151151UL, 0x1F27C9FUL, 0x1F711DFUL, 0x04AFEA4UL, 0x1FFFFFFUL, }; int8_t Levels_BoundLevel(const int8_t level) { return max(level, 0) % LevelCount; } uint32_t Levels_GetLightsForLevel(const int8_t level, const bool setB) { int8_t bLevel = Levels_BoundLevel(level); return setB ? Levels_LightsB[bLevel] : Levels_LightsA[bLevel]; } uint16_t Levels_GetParForLevel(const int8_t level) { return 6 + (Levels_BoundLevel(level) / 5); }

1
src/Levels.h Normal file
View File

@ -0,0 +1 @@
// Copyright (c) Jon Thysell <http://jonthysell.com> // Licensed under the MIT License. #ifndef LEVELS_H #define LEVELS_H #include "stdint.h" #include "stdbool.h" extern const int8_t LevelCount; int8_t Levels_BoundLevel(const int8_t level); uint32_t Levels_GetLightsForLevel(const int8_t level, const bool setB); uint16_t Levels_GetParForLevel(const int8_t level); #endif

1
src/MacLO.c Normal file
View File

@ -0,0 +1 @@
// Copyright (c) Jon Thysell <http://jonthysell.com> // Licensed under the MIT License. #include "Common.h" void InitToolbox() { InitGraf(&thePort); InitFonts(); InitWindows(); InitMenus(); TEInit(); InitDialogs(0L); FlushEvents(everyEvent, 0); InitCursor(); } void InitMainWindow() { MainWindow = GetNewWindow(128, 0L, (WindowPtr)-1L); SetPort(MainWindow); MoveTo(30, 50); DrawString("\pHello MacLO"); } void EventLoop() { while (!Button()) { } } void main(void) { InitToolbox(); InitMainWindow(); EventLoop(); }

BIN
src/MacLO.pi.bin Normal file

Binary file not shown.

BIN
src/MacLO.pi.rsrc.bin Normal file

Binary file not shown.

1
src/stdbool.h Normal file
View File

@ -0,0 +1 @@
// Copyright (c) Jon Thysell <http://jonthysell.com> // Licensed under the MIT License. #ifndef STDBOOL_H #define STDBOOL_H #ifndef true typedef char bool; #define true 1 #define false 0 #endif #endif

1
src/stdint.h Normal file
View File

@ -0,0 +1 @@
// Copyright (c) Jon Thysell <http://jonthysell.com> // Licensed under the MIT License. #ifndef STDINT_H #define STDINT_H #include <limits.h> #if !defined(UINT8_MAX) && defined(UCHAR_MAX) && (UCHAR_MAX) == 0xFFU typedef unsigned char uint8_t; typedef signed char int8_t; #define UINT8_MAX UCHAR_MAX #define INT8_MAX CHAR_MAX #define INT8_MIN CHAR_MIN #endif #if !defined(UINT16_MAX) && defined(USHRT_MAX) && (USHRT_MAX) == 0xFFFFU typedef unsigned short uint16_t; typedef signed short int16_t; #define UINT16_MAX USHRT_MAX #define INT16_MAX SHRT_MAX #define INT16_MIN SHRT_MIN #endif #if !defined(UINT32_MAX) && defined(UINT_MAX) && (UINT_MAX) == 0xFFFFFFFFUL typedef unsigned int uint32_t; typedef signed int int32_t; #define UINT32_MAX UINT_MAX #define INT32_MAX INT_MAX #define INT32_MIN INT_MIN #endif #if !defined(UINT32_MAX) && defined(ULONG_MAX) && (ULONG_MAX) == 0xFFFFFFFFUL typedef unsigned long uint32_t; typedef signed long int32_t; #define UINT32_MAX ULONG_MAX #define INT32_MAX LONG_MAX #define INT32_MIN LONG_MIN #endif #endif