mirror of
https://github.com/SashLilac/cambridge.git
synced 2025-05-13 20:21:25 -05:00
Compare commits
44 Commits
v0.3-beta6
...
v0.3-beta7
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
ffd808e6a0 | ||
|
|
dd96db170e | ||
|
|
7fa547c307 | ||
| b2d0838f90 | |||
|
|
42375cb2b8 | ||
|
|
fe162ed215 | ||
|
|
dda116f00f | ||
|
|
2d3aeeb47d | ||
|
|
784c768c57 | ||
|
|
c18e7ed244 | ||
|
|
9df6bb9989 | ||
|
|
f5873c97bc | ||
|
|
fabdad056e | ||
|
|
0e82a8758c | ||
|
|
e78df19112 | ||
|
|
49775b9578 | ||
|
|
6a3c6ecac0 | ||
|
|
90cf2ebef5 | ||
|
|
799a905a9c | ||
|
|
985f73c39d | ||
|
|
b5db5bbdc3 | ||
|
|
438acde2e2 | ||
|
|
0e1f40ad30 | ||
|
|
6cf6568a57 | ||
|
|
dafc113038 | ||
|
|
923f3d3696 | ||
|
|
db4132bf31 | ||
|
|
c58018dd51 | ||
|
|
c7d0034f9b | ||
|
|
ed5ea72e66 | ||
|
|
dc3ad825dc | ||
|
|
40cba83003 | ||
| a1b3f73787 | |||
|
|
4243d6b2ba | ||
| 33b3ad2889 | |||
|
|
adab1df480 | ||
|
|
711fa830a3 | ||
|
|
c434a3406b | ||
|
|
769b5043e3 | ||
|
|
713c62d807 | ||
|
|
c3f6e34518 | ||
|
|
4d0f6ab9fc | ||
|
|
594aa2620f | ||
|
|
199b535f70 |
1
.gitignore
vendored
1
.gitignore
vendored
@@ -1,5 +1,6 @@
|
|||||||
*.sav
|
*.sav
|
||||||
*.love
|
*.love
|
||||||
|
*.zip
|
||||||
dist/*.zip
|
dist/*.zip
|
||||||
dist/**/cambridge.exe
|
dist/**/cambridge.exe
|
||||||
dist/**/libs
|
dist/**/libs
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
Copyright (c) 2018-2019 Joe Zeng
|
Copyright (c) 2018-2021 Joe Zeng, Ishaan Bhardwaj
|
||||||
|
|
||||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
of this software and associated documentation files (the "Software"), to deal
|
of this software and associated documentation files (the "Software"), to deal
|
||||||
|
|||||||
@@ -98,12 +98,14 @@ Other Notable Games
|
|||||||
- [ZTrix](https://discord.gg/MGhqCBDGNH) by Electra
|
- [ZTrix](https://discord.gg/MGhqCBDGNH) by Electra
|
||||||
- [Shiromino](https://github.com/shiromino/shiromino) by Felicity/nightmareci/kdex
|
- [Shiromino](https://github.com/shiromino/shiromino) by Felicity/nightmareci/kdex
|
||||||
- [Cursed Blocks](https://github.com/Manabender/Cursed-Blocks) by Manabender
|
- [Cursed Blocks](https://github.com/Manabender/Cursed-Blocks) by Manabender
|
||||||
- Picoris 1/2 by MarkGamed
|
- [Picoris 2](https://www.lexaloffle.com/bbs/?tid=41733) by MarkGamed
|
||||||
- [Tetra Online](https://github.com/Juan-Cartes/Tetra-Offline) by Mine
|
- [Tetra Online](https://github.com/Juan-Cartes/Tetra-Offline) by Mine
|
||||||
- [Techmino](https://discord.gg/6Yuww44tq8) by MrZ
|
- [Techmino](https://discord.gg/6Yuww44tq8) by MrZ
|
||||||
|
- [Example Block Game](https://github.com/oshisaure/example-block-game) by Oshisaure
|
||||||
- [TETR.IO](https://tetr.io) by osk
|
- [TETR.IO](https://tetr.io) by osk
|
||||||
- [Master of Blocks](https://discord.gg/72FZ49mjWh) by Phoenix Flare
|
- [Master of Blocks](https://discord.gg/72FZ49mjWh) by Phoenix Flare
|
||||||
- [Spirit Drop](https://rayblastgames.com/spiritdrop.php) by RayRay26
|
- [Spirit Drop](https://rayblastgames.com/spiritdrop.php) by RayRay26
|
||||||
|
- [Puzzle Trial](https://kagamine-rin.itch.io/puzzle-trial) by Rin
|
||||||
- [stackfuse](https://github.com/sinefuse/stackfuse) by sinefuse
|
- [stackfuse](https://github.com/sinefuse/stackfuse) by sinefuse
|
||||||
|
|
||||||

|

|
||||||
|
|||||||
48
SOURCES.md
48
SOURCES.md
@@ -170,3 +170,51 @@ LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
|||||||
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
discord-rpc (https://github.com/discord/discord-rpc)
|
||||||
|
--------------------
|
||||||
|
|
||||||
|
Copyright 2017 Discord, Inc.
|
||||||
|
|
||||||
|
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.
|
||||||
|
|
||||||
|
lua-discordRPC (https://github.com/pfirsich/lua-discordRPC)
|
||||||
|
--------------------
|
||||||
|
|
||||||
|
MIT License
|
||||||
|
|
||||||
|
Copyright (c) 2018 Joel Schumacher
|
||||||
|
|
||||||
|
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.
|
||||||
@@ -7,5 +7,11 @@
|
|||||||
@del dist\win32\SOURCES.md
|
@del dist\win32\SOURCES.md
|
||||||
@del dist\win32\LICENSE.md
|
@del dist\win32\LICENSE.md
|
||||||
@rmdir /Q /S dist\win32\libs
|
@rmdir /Q /S dist\win32\libs
|
||||||
|
@del dist\other\cambridge.love
|
||||||
|
@del dist\other\SOURCES.md
|
||||||
|
@del dist\other\LICENSE.md
|
||||||
|
@rmdir /Q /S dist\other\libs
|
||||||
|
@rmdir /Q /S dist\other
|
||||||
@del dist\cambridge-windows.zip
|
@del dist\cambridge-windows.zip
|
||||||
@del dist\cambridge-win32.zip
|
@del dist\cambridge-win32.zip
|
||||||
|
@del dist\cambridge-other.zip
|
||||||
18
funcs.lua
18
funcs.lua
@@ -1,10 +1,20 @@
|
|||||||
function copy(t)
|
function copy(t)
|
||||||
-- returns deep copy of t (as opposed to the shallow copy you get from var = t)
|
-- returns top-layer shallow copy of t
|
||||||
if type(t) ~= "table" then return t end
|
if type(t) ~= "table" then return t end
|
||||||
local meta = getmetatable(t)
|
|
||||||
local target = {}
|
local target = {}
|
||||||
for k, v in pairs(t) do target[k] = v end
|
for k, v in next, t do target[k] = v end
|
||||||
setmetatable(target, meta)
|
setmetatable(target, getmetatable(t))
|
||||||
|
return target
|
||||||
|
end
|
||||||
|
|
||||||
|
function deepcopy(t)
|
||||||
|
-- returns infinite-layer deep copy of t
|
||||||
|
if type(t) ~= "table" then return t end
|
||||||
|
local target = {}
|
||||||
|
for k, v in next, t do
|
||||||
|
target[deepcopy(k)] = deepcopy(v)
|
||||||
|
end
|
||||||
|
setmetatable(target, deepcopy(getmetatable(t)))
|
||||||
return target
|
return target
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
@@ -2,11 +2,12 @@
|
|||||||
-- If this variable is true, then strict type checking is performed for all
|
-- If this variable is true, then strict type checking is performed for all
|
||||||
-- operations. This may result in slower code, but it will allow you to catch
|
-- operations. This may result in slower code, but it will allow you to catch
|
||||||
-- errors and bugs earlier.
|
-- errors and bugs earlier.
|
||||||
local strict = false
|
local strict = true
|
||||||
|
|
||||||
--------------------------------------------------------------------------------
|
--------------------------------------------------------------------------------
|
||||||
|
|
||||||
local bigint = {}
|
local bigint = {}
|
||||||
|
setmetatable(bigint, {__call = function(_, arg) return bigint.new(arg) end})
|
||||||
|
|
||||||
local mt = {
|
local mt = {
|
||||||
__add = function(lhs, rhs)
|
__add = function(lhs, rhs)
|
||||||
@@ -76,7 +77,7 @@ function bigint.new(num)
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
return self
|
return bigint.strip(self)
|
||||||
end
|
end
|
||||||
|
|
||||||
-- Check the type of a big
|
-- Check the type of a big
|
||||||
@@ -96,6 +97,14 @@ function bigint.check(big, force)
|
|||||||
return true
|
return true
|
||||||
end
|
end
|
||||||
|
|
||||||
|
-- Strip leading zeroes from a big, but don't remove the last zero
|
||||||
|
function bigint.strip(big)
|
||||||
|
while (#big.digits > 1) and (big.digits[1] == 0) do
|
||||||
|
table.remove(big.digits, 1)
|
||||||
|
end
|
||||||
|
return big
|
||||||
|
end
|
||||||
|
|
||||||
-- Return a new big with the same digits but with a positive sign (absolute
|
-- Return a new big with the same digits but with a positive sign (absolute
|
||||||
-- value)
|
-- value)
|
||||||
function bigint.abs(big)
|
function bigint.abs(big)
|
||||||
@@ -329,12 +338,7 @@ function bigint.subtract_raw(big1, big2)
|
|||||||
----------------------------------------------------------------------------
|
----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
-- Strip leading zeroes if any, but not if 0 is the only digit
|
return bigint.strip(result)
|
||||||
while (#result.digits > 1) and (result.digits[1] == 0) do
|
|
||||||
table.remove(result.digits, 1)
|
|
||||||
end
|
|
||||||
|
|
||||||
return result
|
|
||||||
end
|
end
|
||||||
|
|
||||||
-- FRONTEND: Addition and subtraction operations, accounting for signs
|
-- FRONTEND: Addition and subtraction operations, accounting for signs
|
||||||
@@ -364,6 +368,7 @@ function bigint.add(big1, big2)
|
|||||||
|
|
||||||
return result
|
return result
|
||||||
end
|
end
|
||||||
|
|
||||||
function bigint.subtract(big1, big2)
|
function bigint.subtract(big1, big2)
|
||||||
-- Type checking is done by bigint.compare in bigint.add
|
-- Type checking is done by bigint.compare in bigint.add
|
||||||
-- Subtracting is like adding a negative
|
-- Subtracting is like adding a negative
|
||||||
@@ -460,7 +465,7 @@ end
|
|||||||
function bigint.exponentiate(big, power)
|
function bigint.exponentiate(big, power)
|
||||||
-- Type checking for big done by bigint.multiply
|
-- Type checking for big done by bigint.multiply
|
||||||
assert(bigint.compare(power, bigint.new(0), ">="),
|
assert(bigint.compare(power, bigint.new(0), ">="),
|
||||||
" negative powers are not supported")
|
"negative powers are not supported")
|
||||||
local exp = power:clone()
|
local exp = power:clone()
|
||||||
|
|
||||||
if (bigint.compare(exp, bigint.new(0), "==")) then
|
if (bigint.compare(exp, bigint.new(0), "==")) then
|
||||||
@@ -530,12 +535,7 @@ function bigint.divide_raw(big1, big2)
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
-- Remove leading zeros from result
|
return bigint.strip(result), dividend
|
||||||
while (result.digits[1] == 0) do
|
|
||||||
table.remove(result.digits, 1)
|
|
||||||
end
|
|
||||||
|
|
||||||
return result, dividend
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
@@ -24,6 +24,59 @@ if osname == "Linux" then
|
|||||||
elseif osname == "OS X" then
|
elseif osname == "OS X" then
|
||||||
discordRPClib = ffi.load(source.."/libs/discord-rpc.dylib")
|
discordRPClib = ffi.load(source.."/libs/discord-rpc.dylib")
|
||||||
elseif osname == "Windows" then
|
elseif osname == "Windows" then
|
||||||
|
-- I would strongly advise never touching this. It was not trivial to get correct. -nightmareci
|
||||||
|
|
||||||
|
ffi.cdef[[
|
||||||
|
typedef uint32_t DWORD;
|
||||||
|
typedef char CHAR;
|
||||||
|
typedef CHAR *LPSTR;
|
||||||
|
typedef const CHAR *LPCSTR;
|
||||||
|
typedef wchar_t WCHAR;
|
||||||
|
typedef WCHAR *LPWSTR;
|
||||||
|
typedef LPWSTR PWSTR;
|
||||||
|
typedef const WCHAR *LPCWSTR;
|
||||||
|
|
||||||
|
static const DWORD CP_UTF8 = 65001;
|
||||||
|
int32_t MultiByteToWideChar(
|
||||||
|
DWORD CodePage,
|
||||||
|
DWORD dwFlags,
|
||||||
|
LPCSTR lpMultiByteStr,
|
||||||
|
int32_t cbMultiByte,
|
||||||
|
LPWSTR lpWideCharStr,
|
||||||
|
int32_t cchWideChar
|
||||||
|
);
|
||||||
|
|
||||||
|
int32_t WideCharToMultiByte(
|
||||||
|
DWORD CodePage,
|
||||||
|
DWORD dwFlags,
|
||||||
|
LPCWSTR lpWideCharStr,
|
||||||
|
int32_t cchWideChar,
|
||||||
|
LPSTR lpMultiByteStr,
|
||||||
|
int32_t cbMultiByte,
|
||||||
|
void* lpDefaultChar,
|
||||||
|
void* lpUsedDefaultChar
|
||||||
|
);
|
||||||
|
|
||||||
|
DWORD GetShortPathNameW(
|
||||||
|
LPCWSTR lpszLongPath,
|
||||||
|
LPWSTR lpszShortPath,
|
||||||
|
DWORD cchBuffer
|
||||||
|
);
|
||||||
|
]]
|
||||||
|
|
||||||
|
local originalWideSize = ffi.C.MultiByteToWideChar(ffi.C.CP_UTF8, 0, source, -1, nil, 0)
|
||||||
|
local originalWide = ffi.new('WCHAR[?]', originalWideSize)
|
||||||
|
ffi.C.MultiByteToWideChar(ffi.C.CP_UTF8, 0, source, -1, originalWide, originalWideSize)
|
||||||
|
|
||||||
|
local sourceSize = ffi.C.GetShortPathNameW(originalWide, nil, 0)
|
||||||
|
local sourceWide = ffi.new('WCHAR[?]', sourceSize)
|
||||||
|
ffi.C.GetShortPathNameW(originalWide, sourceWide, sourceSize)
|
||||||
|
|
||||||
|
local sourceChar = ffi.new('char[?]', sourceSize)
|
||||||
|
ffi.C.WideCharToMultiByte(ffi.C.CP_UTF8, 0, sourceWide, sourceSize, sourceChar, sourceSize, nil, nil)
|
||||||
|
|
||||||
|
source = ffi.string(sourceChar)
|
||||||
|
|
||||||
discordRPClib = ffi.load(source.."/libs/discord-rpc.dll")
|
discordRPClib = ffi.load(source.."/libs/discord-rpc.dll")
|
||||||
else
|
else
|
||||||
-- Else it crashes later on
|
-- Else it crashes later on
|
||||||
|
|||||||
14
load/bgm.lua
14
load/bgm.lua
@@ -7,6 +7,7 @@ bgm = {
|
|||||||
|
|
||||||
local current_bgm = nil
|
local current_bgm = nil
|
||||||
local bgm_locked = false
|
local bgm_locked = false
|
||||||
|
local unfocused = false
|
||||||
|
|
||||||
function switchBGM(sound, subsound)
|
function switchBGM(sound, subsound)
|
||||||
if current_bgm ~= nil then
|
if current_bgm ~= nil then
|
||||||
@@ -56,7 +57,7 @@ end
|
|||||||
function resetBGMFadeout(time)
|
function resetBGMFadeout(time)
|
||||||
current_bgm:setVolume(config.bgm_volume)
|
current_bgm:setVolume(config.bgm_volume)
|
||||||
fading_bgm = false
|
fading_bgm = false
|
||||||
current_bgm:play()
|
resumeBGM()
|
||||||
end
|
end
|
||||||
|
|
||||||
function processBGMFadeout(dt)
|
function processBGMFadeout(dt)
|
||||||
@@ -70,13 +71,20 @@ function processBGMFadeout(dt)
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function pauseBGM()
|
function pauseBGM(f)
|
||||||
|
if f then
|
||||||
|
unfocused = true
|
||||||
|
end
|
||||||
if current_bgm ~= nil then
|
if current_bgm ~= nil then
|
||||||
current_bgm:pause()
|
current_bgm:pause()
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function resumeBGM()
|
function resumeBGM(f)
|
||||||
|
if f and scene.paused and unfocused then
|
||||||
|
unfocused = false
|
||||||
|
return
|
||||||
|
end
|
||||||
if current_bgm ~= nil then
|
if current_bgm ~= nil then
|
||||||
current_bgm:play()
|
current_bgm:play()
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -25,6 +25,15 @@ backgrounds = {
|
|||||||
game_config = love.graphics.newImage("res/backgrounds/options-game.png"),
|
game_config = love.graphics.newImage("res/backgrounds/options-game.png"),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
-- in order, the colors are:
|
||||||
|
-- red, orange, yellow, green, cyan, blue
|
||||||
|
-- magenta (or purple), white, black
|
||||||
|
-- the next three don't have colors tied to them
|
||||||
|
-- F is used for lock flash
|
||||||
|
-- A is a garbage block
|
||||||
|
-- X is an invisible "block"
|
||||||
|
-- don't use these for piece colors when making a ruleset
|
||||||
|
-- all the others are fine to use
|
||||||
blocks = {
|
blocks = {
|
||||||
["2tie"] = {
|
["2tie"] = {
|
||||||
R = love.graphics.newImage("res/img/s1.png"),
|
R = love.graphics.newImage("res/img/s1.png"),
|
||||||
@@ -34,6 +43,8 @@ blocks = {
|
|||||||
C = love.graphics.newImage("res/img/s2.png"),
|
C = love.graphics.newImage("res/img/s2.png"),
|
||||||
B = love.graphics.newImage("res/img/s4.png"),
|
B = love.graphics.newImage("res/img/s4.png"),
|
||||||
M = love.graphics.newImage("res/img/s5.png"),
|
M = love.graphics.newImage("res/img/s5.png"),
|
||||||
|
W = love.graphics.newImage("res/img/s9.png"),
|
||||||
|
D = love.graphics.newImage("res/img/s8.png"),
|
||||||
F = love.graphics.newImage("res/img/s9.png"),
|
F = love.graphics.newImage("res/img/s9.png"),
|
||||||
A = love.graphics.newImage("res/img/s8.png"),
|
A = love.graphics.newImage("res/img/s8.png"),
|
||||||
X = love.graphics.newImage("res/img/s9.png"),
|
X = love.graphics.newImage("res/img/s9.png"),
|
||||||
@@ -46,6 +57,8 @@ blocks = {
|
|||||||
C = love.graphics.newImage("res/img/bone.png"),
|
C = love.graphics.newImage("res/img/bone.png"),
|
||||||
B = love.graphics.newImage("res/img/bone.png"),
|
B = love.graphics.newImage("res/img/bone.png"),
|
||||||
M = love.graphics.newImage("res/img/bone.png"),
|
M = love.graphics.newImage("res/img/bone.png"),
|
||||||
|
W = love.graphics.newImage("res/img/bone.png"),
|
||||||
|
D = love.graphics.newImage("res/img/bone.png"),
|
||||||
F = love.graphics.newImage("res/img/bone.png"),
|
F = love.graphics.newImage("res/img/bone.png"),
|
||||||
A = love.graphics.newImage("res/img/bone.png"),
|
A = love.graphics.newImage("res/img/bone.png"),
|
||||||
X = love.graphics.newImage("res/img/bone.png"),
|
X = love.graphics.newImage("res/img/bone.png"),
|
||||||
@@ -58,13 +71,16 @@ blocks = {
|
|||||||
C = love.graphics.newImage("res/img/gem2.png"),
|
C = love.graphics.newImage("res/img/gem2.png"),
|
||||||
B = love.graphics.newImage("res/img/gem4.png"),
|
B = love.graphics.newImage("res/img/gem4.png"),
|
||||||
M = love.graphics.newImage("res/img/gem5.png"),
|
M = love.graphics.newImage("res/img/gem5.png"),
|
||||||
|
W = love.graphics.newImage("res/img/gem9.png"),
|
||||||
|
D = love.graphics.newImage("res/img/gem9.png"),
|
||||||
F = love.graphics.newImage("res/img/gem9.png"),
|
F = love.graphics.newImage("res/img/gem9.png"),
|
||||||
A = love.graphics.newImage("res/img/gem9.png"),
|
A = love.graphics.newImage("res/img/gem9.png"),
|
||||||
X = love.graphics.newImage("res/img/gem9.png"),
|
X = love.graphics.newImage("res/img/gem9.png"),
|
||||||
},
|
},
|
||||||
["square"] = {
|
["square"] = {
|
||||||
F = love.graphics.newImage("res/img/squares.png"),
|
W = love.graphics.newImage("res/img/squares.png"),
|
||||||
Y = love.graphics.newImage("res/img/squareg.png"),
|
Y = love.graphics.newImage("res/img/squareg.png"),
|
||||||
|
F = love.graphics.newImage("res/img/squares.png"),
|
||||||
X = love.graphics.newImage("res/img/squares.png"),
|
X = love.graphics.newImage("res/img/squares.png"),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -87,7 +103,7 @@ ColourSchemes = {
|
|||||||
Z = "R",
|
Z = "R",
|
||||||
O = "Y",
|
O = "Y",
|
||||||
T = "M",
|
T = "M",
|
||||||
},
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
for name, blockset in pairs(blocks) do
|
for name, blockset in pairs(blocks) do
|
||||||
|
|||||||
@@ -1,23 +1,16 @@
|
|||||||
local binser = require 'libs.binser'
|
local binser = require 'libs.binser'
|
||||||
|
|
||||||
function loadSave()
|
function loadSave()
|
||||||
local info = love.filesystem.getInfo(
|
config = loadFromFile('config.sav')
|
||||||
love.filesystem.getSaveDirectory(), "directory"
|
highscores = loadFromFile('highscores.sav')
|
||||||
)
|
|
||||||
if not info then
|
|
||||||
love.filesystem.remove(love.filesystem.getSaveDirectory())
|
|
||||||
love.filesystem.createDirectory(love.filesystem.getSaveDirectory())
|
|
||||||
end
|
|
||||||
config = loadFromFile(
|
|
||||||
love.filesystem.getSaveDirectory() .. '/config.sav'
|
|
||||||
)
|
|
||||||
highscores = loadFromFile(
|
|
||||||
love.filesystem.getSaveDirectory() .. '/highscores.sav'
|
|
||||||
)
|
|
||||||
end
|
end
|
||||||
|
|
||||||
function loadFromFile(filename)
|
function loadFromFile(filename)
|
||||||
local save_data, len = binser.readFile(filename)
|
local file_data = love.filesystem.read(filename)
|
||||||
|
if file_data == nil then
|
||||||
|
return {} -- new object
|
||||||
|
end
|
||||||
|
local save_data = binser.deserialize(file_data)
|
||||||
if save_data == nil then
|
if save_data == nil then
|
||||||
return {} -- new object
|
return {} -- new object
|
||||||
end
|
end
|
||||||
@@ -51,13 +44,13 @@ function initConfig()
|
|||||||
end
|
end
|
||||||
|
|
||||||
function saveConfig()
|
function saveConfig()
|
||||||
binser.writeFile(
|
love.filesystem.write(
|
||||||
love.filesystem.getSaveDirectory() .. '/config.sav', config
|
'config.sav', binser.serialize(config)
|
||||||
)
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
function saveHighscores()
|
function saveHighscores()
|
||||||
binser.writeFile(
|
love.filesystem.write(
|
||||||
love.filesystem.getSaveDirectory() .. '/highscores.sav', highscores
|
'highscores.sav', binser.serialize(highscores)
|
||||||
)
|
)
|
||||||
end
|
end
|
||||||
|
|||||||
17
main.lua
17
main.lua
@@ -10,6 +10,7 @@ function love.load()
|
|||||||
require "load.bigint"
|
require "load.bigint"
|
||||||
require "load.version"
|
require "load.version"
|
||||||
loadSave()
|
loadSave()
|
||||||
|
require "funcs"
|
||||||
require "scene"
|
require "scene"
|
||||||
|
|
||||||
--config["side_next"] = false
|
--config["side_next"] = false
|
||||||
@@ -36,14 +37,14 @@ function initModules()
|
|||||||
game_modes = {}
|
game_modes = {}
|
||||||
mode_list = love.filesystem.getDirectoryItems("tetris/modes")
|
mode_list = love.filesystem.getDirectoryItems("tetris/modes")
|
||||||
for i=1,#mode_list do
|
for i=1,#mode_list do
|
||||||
if(mode_list[i] ~= "gamemode.lua" and mode_list[i] ~= "unrefactored_modes") then
|
if(mode_list[i] ~= "gamemode.lua" and string.sub(mode_list[i], -4) == ".lua") then
|
||||||
game_modes[#game_modes+1] = require ("tetris.modes."..string.sub(mode_list[i],1,-5))
|
game_modes[#game_modes+1] = require ("tetris.modes."..string.sub(mode_list[i],1,-5))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
rulesets = {}
|
rulesets = {}
|
||||||
rule_list = love.filesystem.getDirectoryItems("tetris/rulesets")
|
rule_list = love.filesystem.getDirectoryItems("tetris/rulesets")
|
||||||
for i=1,#rule_list do
|
for i=1,#rule_list do
|
||||||
if(rule_list[i] ~= "ruleset.lua" and rule_list[i] ~= "unrefactored_rulesets") then
|
if(rule_list[i] ~= "ruleset.lua" and string.sub(rule_list[i], -4) == ".lua") then
|
||||||
rulesets[#rulesets+1] = require ("tetris.rulesets."..string.sub(rule_list[i],1,-5))
|
rulesets[#rulesets+1] = require ("tetris.rulesets."..string.sub(rule_list[i],1,-5))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@@ -82,7 +83,7 @@ end
|
|||||||
|
|
||||||
function love.keypressed(key, scancode)
|
function love.keypressed(key, scancode)
|
||||||
-- global hotkeys
|
-- global hotkeys
|
||||||
if scancode == "f4" then
|
if scancode == "f11" then
|
||||||
config["fullscreen"] = not config["fullscreen"]
|
config["fullscreen"] = not config["fullscreen"]
|
||||||
saveConfig()
|
saveConfig()
|
||||||
love.window.setFullscreen(config["fullscreen"])
|
love.window.setFullscreen(config["fullscreen"])
|
||||||
@@ -258,11 +259,15 @@ function love.joystickhat(joystick, hat, direction)
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
function love.wheelmoved(x, y)
|
||||||
|
scene:onInputPress({input=nil, type="wheel", x=x, y=y})
|
||||||
|
end
|
||||||
|
|
||||||
function love.focus(f)
|
function love.focus(f)
|
||||||
if f and (scene.title ~= "Game" or not scene.paused) then
|
if f then
|
||||||
resumeBGM()
|
resumeBGM(true)
|
||||||
else
|
else
|
||||||
pauseBGM()
|
pauseBGM(true)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
4
release
4
release
@@ -2,8 +2,10 @@
|
|||||||
mkdir dist
|
mkdir dist
|
||||||
mkdir dist/windows
|
mkdir dist/windows
|
||||||
mkdir dist/win32
|
mkdir dist/win32
|
||||||
cp cambridge.love dist/
|
mkdir dist/other
|
||||||
cat dist/windows/love.exe cambridge.love > dist/windows/cambridge.exe
|
cat dist/windows/love.exe cambridge.love > dist/windows/cambridge.exe
|
||||||
zip dist/cambridge-windows.zip dist/windows/* SOURCES.md LICENSE.md
|
zip dist/cambridge-windows.zip dist/windows/* SOURCES.md LICENSE.md
|
||||||
cat dist/win32/love.exe cambridge.love > dist/win32/cambridge.exe
|
cat dist/win32/love.exe cambridge.love > dist/win32/cambridge.exe
|
||||||
zip dist/cambridge-win32.zip dist/win32/* SOURCES.md LICENSE.md
|
zip dist/cambridge-win32.zip dist/win32/* SOURCES.md LICENSE.md
|
||||||
|
cp cambridge.love dist/other/
|
||||||
|
zip dist/cambridge-other.zip cambridge.love libs/discord-rpc.* SOURCES.md LICENSE.md
|
||||||
10
release.bat
10
release.bat
@@ -5,17 +5,23 @@ mkdir dist\windows
|
|||||||
mkdir dist\windows\libs
|
mkdir dist\windows\libs
|
||||||
mkdir dist\win32
|
mkdir dist\win32
|
||||||
mkdir dist\win32\libs
|
mkdir dist\win32\libs
|
||||||
|
mkdir dist\other
|
||||||
|
mkdir dist\other\libs
|
||||||
|
|
||||||
copy /b dist\windows\love.exe+cambridge.love dist\windows\cambridge.exe
|
copy /b dist\windows\love.exe+cambridge.love dist\windows\cambridge.exe
|
||||||
copy /b dist\win32\love.exe+cambridge.love dist\win32\cambridge.exe
|
copy /b dist\win32\love.exe+cambridge.love dist\win32\cambridge.exe
|
||||||
|
copy /b cambridge.love dist\other\cambridge.love
|
||||||
|
|
||||||
copy libs\discord-rpc.dll dist\windows\libs
|
copy libs\discord-rpc.dll dist\windows\libs
|
||||||
copy libs\discord-rpc.dll dist\win32\libs
|
copy libs\discord-rpc.dll dist\win32\libs
|
||||||
|
copy libs\discord-rpc.* dist\other\libs
|
||||||
|
|
||||||
copy SOURCES.md dist\windows
|
copy SOURCES.md dist\windows
|
||||||
copy LICENSE.md dist\windows
|
copy LICENSE.md dist\windows
|
||||||
copy SOURCES.md dist\win32
|
copy SOURCES.md dist\win32
|
||||||
copy LICENSE.md dist\win32
|
copy LICENSE.md dist\win32
|
||||||
|
copy SOURCES.md dist\other
|
||||||
|
copy LICENSE.md dist\other
|
||||||
|
|
||||||
cd dist\windows
|
cd dist\windows
|
||||||
tar -a -c -f ..\cambridge-windows.zip cambridge.exe *.dll libs *.md
|
tar -a -c -f ..\cambridge-windows.zip cambridge.exe *.dll libs *.md
|
||||||
@@ -24,3 +30,7 @@ cd ..\..
|
|||||||
cd dist\win32
|
cd dist\win32
|
||||||
tar -a -c -f ..\cambridge-win32.zip cambridge.exe *.dll libs *.md
|
tar -a -c -f ..\cambridge-win32.zip cambridge.exe *.dll libs *.md
|
||||||
cd ..\..
|
cd ..\..
|
||||||
|
|
||||||
|
cd dist\other
|
||||||
|
tar -a -c -f ..\cambridge-other.zip cambridge.love libs *.md
|
||||||
|
cd ..\..
|
||||||
BIN
res/img/bone.png
BIN
res/img/bone.png
Binary file not shown.
|
Before Width: | Height: | Size: 188 B After Width: | Height: | Size: 151 B |
Binary file not shown.
|
Before Width: | Height: | Size: 153 B After Width: | Height: | Size: 151 B |
Binary file not shown.
|
Before Width: | Height: | Size: 926 B After Width: | Height: | Size: 1.1 KiB |
@@ -5,7 +5,7 @@ CreditsScene.title = "Credits"
|
|||||||
function CreditsScene:new()
|
function CreditsScene:new()
|
||||||
self.frames = 0
|
self.frames = 0
|
||||||
-- higher = slower
|
-- higher = slower
|
||||||
self.scroll_speed = 1.9
|
self.scroll_speed = 1.85
|
||||||
switchBGM("credit_roll", "gm3")
|
switchBGM("credit_roll", "gm3")
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -34,14 +34,14 @@ function CreditsScene:render()
|
|||||||
|
|
||||||
love.graphics.setFont(font_3x5_4)
|
love.graphics.setFont(font_3x5_4)
|
||||||
love.graphics.print("Cambridge Credits", 320, 500 - offset)
|
love.graphics.print("Cambridge Credits", 320, 500 - offset)
|
||||||
love.graphics.print("THANK YOU\nFOR PLAYING!", 320, math.max(2010 - offset, 240))
|
love.graphics.print("THANK YOU\nFOR PLAYING!", 320, math.max(2030 - offset, 240))
|
||||||
|
|
||||||
love.graphics.setFont(font_3x5_3)
|
love.graphics.setFont(font_3x5_3)
|
||||||
love.graphics.print("Game Developers", 320, 550 - offset)
|
love.graphics.print("Game Developers", 320, 550 - offset)
|
||||||
love.graphics.print("Project Heads", 320, 640 - offset)
|
love.graphics.print("Project Heads", 320, 640 - offset)
|
||||||
love.graphics.print("Notable Game Developers", 320, 730 - offset)
|
love.graphics.print("Notable Game Developers", 320, 730 - offset)
|
||||||
love.graphics.print("Special Thanks", 320, 980 - offset)
|
love.graphics.print("Special Thanks", 320, 1000 - offset)
|
||||||
love.graphics.print("- Milla", 320, math.max(2090 - offset, 320))
|
love.graphics.print("- Milla", 320, math.max(2110 - offset, 320))
|
||||||
|
|
||||||
love.graphics.setFont(font_3x5_2)
|
love.graphics.setFont(font_3x5_2)
|
||||||
love.graphics.print("Oshisaure\nJoe Zeng", 320, 590 - offset)
|
love.graphics.print("Oshisaure\nJoe Zeng", 320, 590 - offset)
|
||||||
@@ -51,7 +51,7 @@ function CreditsScene:render()
|
|||||||
"Electra - ZTrix\nFelicity/nightmareci/kdex - Shiromino\n" ..
|
"Electra - ZTrix\nFelicity/nightmareci/kdex - Shiromino\n" ..
|
||||||
"Mine - Tetra Online\nMrZ - Techmino\nosk - TETR.IO\n" ..
|
"Mine - Tetra Online\nMrZ - Techmino\nosk - TETR.IO\n" ..
|
||||||
"Phoenix Flare - Master of Blocks\nRayRay26 - Spirit Drop\n" ..
|
"Phoenix Flare - Master of Blocks\nRayRay26 - Spirit Drop\n" ..
|
||||||
"sinefuse - stackfuse",
|
"Rin - Puzzle Trial\nsinefuse - stackfuse",
|
||||||
320, 770 - offset
|
320, 770 - offset
|
||||||
)
|
)
|
||||||
love.graphics.print(
|
love.graphics.print(
|
||||||
@@ -69,7 +69,7 @@ function CreditsScene:render()
|
|||||||
"Tetra Legends Discord\nTetra Online Discord\nMultimino Discord\n" ..
|
"Tetra Legends Discord\nTetra Online Discord\nMultimino Discord\n" ..
|
||||||
"Hard Drop Discord\nRusty's Systemspace\nCambridge Discord\n" ..
|
"Hard Drop Discord\nRusty's Systemspace\nCambridge Discord\n" ..
|
||||||
"And to you, the player!",
|
"And to you, the player!",
|
||||||
320, 1020 - offset
|
320, 1040 - offset
|
||||||
)
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
@@ -100,9 +100,10 @@ function ConfigScene:onInputPress(e)
|
|||||||
local option = ConfigScene.options[self.highlight]
|
local option = ConfigScene.options[self.highlight]
|
||||||
config.gamesettings[option[1]] = Mod1(config.gamesettings[option[1]]-1, #option[4])
|
config.gamesettings[option[1]] = Mod1(config.gamesettings[option[1]]-1, #option[4])
|
||||||
else
|
else
|
||||||
playSE("cursor")
|
local sld = self[self.options[self.highlight][4]]
|
||||||
sld = self[self.options[self.highlight][4]]
|
|
||||||
sld.value = math.max(sld.min, math.min(sld.max, (sld:getValue() - 5) / (sld.max - sld.min)))
|
sld.value = math.max(sld.min, math.min(sld.max, (sld:getValue() - 5) / (sld.max - sld.min)))
|
||||||
|
sld:update()
|
||||||
|
playSE("cursor")
|
||||||
end
|
end
|
||||||
elseif e.input == "right" or e.scancode == "right" then
|
elseif e.input == "right" or e.scancode == "right" then
|
||||||
if not self.options[self.highlight][3] then
|
if not self.options[self.highlight][3] then
|
||||||
@@ -110,9 +111,10 @@ function ConfigScene:onInputPress(e)
|
|||||||
local option = ConfigScene.options[self.highlight]
|
local option = ConfigScene.options[self.highlight]
|
||||||
config.gamesettings[option[1]] = Mod1(config.gamesettings[option[1]]+1, #option[4])
|
config.gamesettings[option[1]] = Mod1(config.gamesettings[option[1]]+1, #option[4])
|
||||||
else
|
else
|
||||||
playSE("cursor")
|
|
||||||
sld = self[self.options[self.highlight][4]]
|
sld = self[self.options[self.highlight][4]]
|
||||||
sld.value = math.max(sld.min, math.min(sld.max, (sld:getValue() + 5) / (sld.max - sld.min)))--math.max(0, (math.floor(sld:getValue())+2)/(sld.max-sld.min))
|
sld.value = math.max(sld.min, math.min(sld.max, (sld:getValue() + 5) / (sld.max - sld.min)))
|
||||||
|
sld:update()
|
||||||
|
playSE("cursor")
|
||||||
end
|
end
|
||||||
elseif e.input == "menu_back" or e.scancode == "delete" or e.scancode == "backspace" then
|
elseif e.input == "menu_back" or e.scancode == "delete" or e.scancode == "backspace" then
|
||||||
loadSave()
|
loadSave()
|
||||||
|
|||||||
@@ -6,6 +6,22 @@ current_mode = 1
|
|||||||
current_ruleset = 1
|
current_ruleset = 1
|
||||||
|
|
||||||
function ModeSelectScene:new()
|
function ModeSelectScene:new()
|
||||||
|
-- reload custom modules
|
||||||
|
initModules()
|
||||||
|
if table.getn(game_modes) == 0 or table.getn(rulesets) == 0 then
|
||||||
|
self.display_warning = true
|
||||||
|
current_mode = 1
|
||||||
|
current_ruleset = 1
|
||||||
|
else
|
||||||
|
self.display_warning = false
|
||||||
|
if current_mode > table.getn(game_modes) then
|
||||||
|
current_mode = 1
|
||||||
|
end
|
||||||
|
if current_ruleset > table.getn(rulesets) then
|
||||||
|
current_ruleset = 1
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
self.menu_state = {
|
self.menu_state = {
|
||||||
mode = current_mode,
|
mode = current_mode,
|
||||||
ruleset = current_ruleset,
|
ruleset = current_ruleset,
|
||||||
@@ -19,6 +35,7 @@ function ModeSelectScene:new()
|
|||||||
rotate_180 = false,
|
rotate_180 = false,
|
||||||
hold = false,
|
hold = false,
|
||||||
}
|
}
|
||||||
|
self.das = 0
|
||||||
DiscordRPC:update({
|
DiscordRPC:update({
|
||||||
details = "In menus",
|
details = "In menus",
|
||||||
state = "Choosing a mode",
|
state = "Choosing a mode",
|
||||||
@@ -27,6 +44,17 @@ end
|
|||||||
|
|
||||||
function ModeSelectScene:update()
|
function ModeSelectScene:update()
|
||||||
switchBGM(nil) -- experimental
|
switchBGM(nil) -- experimental
|
||||||
|
|
||||||
|
if self.das_up or self.das_down then
|
||||||
|
self.das = self.das + 1
|
||||||
|
else
|
||||||
|
self.das = 0
|
||||||
|
end
|
||||||
|
|
||||||
|
if self.das >= 15 then
|
||||||
|
self:changeOption(self.das_up and -1 or 1)
|
||||||
|
self.das = self.das - 4
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function ModeSelectScene:render()
|
function ModeSelectScene:render()
|
||||||
@@ -36,6 +64,23 @@ function ModeSelectScene:render()
|
|||||||
0.5, 0.5
|
0.5, 0.5
|
||||||
)
|
)
|
||||||
|
|
||||||
|
love.graphics.draw(misc_graphics["select_mode"], 20, 40)
|
||||||
|
|
||||||
|
if self.display_warning then
|
||||||
|
love.graphics.setFont(font_3x5_3)
|
||||||
|
love.graphics.printf(
|
||||||
|
"You have no modes or rulesets.",
|
||||||
|
80, 200, 480, "center"
|
||||||
|
)
|
||||||
|
love.graphics.setFont(font_3x5_2)
|
||||||
|
love.graphics.printf(
|
||||||
|
"Come back to this menu after getting more modes or rulesets. " ..
|
||||||
|
"Press any button to return to the main menu.",
|
||||||
|
80, 250, 480, "center"
|
||||||
|
)
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
if self.menu_state.select == "mode" then
|
if self.menu_state.select == "mode" then
|
||||||
love.graphics.setColor(1, 1, 1, 0.5)
|
love.graphics.setColor(1, 1, 1, 0.5)
|
||||||
elseif self.menu_state.select == "ruleset" then
|
elseif self.menu_state.select == "ruleset" then
|
||||||
@@ -52,8 +97,6 @@ function ModeSelectScene:render()
|
|||||||
|
|
||||||
love.graphics.setColor(1, 1, 1, 1)
|
love.graphics.setColor(1, 1, 1, 1)
|
||||||
|
|
||||||
love.graphics.draw(misc_graphics["select_mode"], 20, 40)
|
|
||||||
|
|
||||||
love.graphics.setFont(font_3x5_2)
|
love.graphics.setFont(font_3x5_2)
|
||||||
for idx, mode in pairs(game_modes) do
|
for idx, mode in pairs(game_modes) do
|
||||||
if(idx >= self.menu_state.mode-9 and idx <= self.menu_state.mode+9) then
|
if(idx >= self.menu_state.mode-9 and idx <= self.menu_state.mode+9) then
|
||||||
@@ -68,23 +111,37 @@ function ModeSelectScene:render()
|
|||||||
end
|
end
|
||||||
|
|
||||||
function ModeSelectScene:onInputPress(e)
|
function ModeSelectScene:onInputPress(e)
|
||||||
if e.input == "menu_decide" or e.scancode == "return" then
|
if self.display_warning and e.input then
|
||||||
|
scene = TitleScene()
|
||||||
|
elseif e.type == "wheel" then
|
||||||
|
if e.x % 2 == 1 then
|
||||||
|
self:switchSelect()
|
||||||
|
end
|
||||||
|
if e.y ~= 0 then
|
||||||
|
self:changeOption(-e.y)
|
||||||
|
end
|
||||||
|
elseif e.input == "menu_decide" or e.scancode == "return" then
|
||||||
current_mode = self.menu_state.mode
|
current_mode = self.menu_state.mode
|
||||||
current_ruleset = self.menu_state.ruleset
|
current_ruleset = self.menu_state.ruleset
|
||||||
config.current_mode = current_mode
|
config.current_mode = current_mode
|
||||||
config.current_ruleset = current_ruleset
|
config.current_ruleset = current_ruleset
|
||||||
playSE("mode_decide")
|
playSE("mode_decide")
|
||||||
saveConfig()
|
saveConfig()
|
||||||
scene = GameScene(game_modes[self.menu_state.mode], rulesets[self.menu_state.ruleset], self.secret_inputs)
|
scene = GameScene(
|
||||||
|
game_modes[self.menu_state.mode],
|
||||||
|
rulesets[self.menu_state.ruleset],
|
||||||
|
self.secret_inputs
|
||||||
|
)
|
||||||
elseif e.input == "up" or e.scancode == "up" then
|
elseif e.input == "up" or e.scancode == "up" then
|
||||||
self:changeOption(-1)
|
self:changeOption(-1)
|
||||||
playSE("cursor")
|
self.das_up = true
|
||||||
|
self.das_down = nil
|
||||||
elseif e.input == "down" or e.scancode == "down" then
|
elseif e.input == "down" or e.scancode == "down" then
|
||||||
self:changeOption(1)
|
self:changeOption(1)
|
||||||
playSE("cursor")
|
self.das_down = true
|
||||||
|
self.das_up = nil
|
||||||
elseif e.input == "left" or e.input == "right" or e.scancode == "left" or e.scancode == "right" then
|
elseif e.input == "left" or e.input == "right" or e.scancode == "left" or e.scancode == "right" then
|
||||||
self:switchSelect()
|
self:switchSelect()
|
||||||
playSE("cursor_lr")
|
|
||||||
elseif e.input == "menu_back" or e.scancode == "delete" or e.scancode == "backspace" then
|
elseif e.input == "menu_back" or e.scancode == "delete" or e.scancode == "backspace" then
|
||||||
scene = TitleScene()
|
scene = TitleScene()
|
||||||
elseif e.input then
|
elseif e.input then
|
||||||
@@ -95,6 +152,10 @@ end
|
|||||||
function ModeSelectScene:onInputRelease(e)
|
function ModeSelectScene:onInputRelease(e)
|
||||||
if e.input == "hold" or (e.input and string.sub(e.input, 1, 7) == "rotate_") then
|
if e.input == "hold" or (e.input and string.sub(e.input, 1, 7) == "rotate_") then
|
||||||
self.secret_inputs[e.input] = false
|
self.secret_inputs[e.input] = false
|
||||||
|
elseif e.input == "up" or e.scancode == "up" then
|
||||||
|
self.das_up = nil
|
||||||
|
elseif e.input == "down" or e.scancode == "down" then
|
||||||
|
self.das_down = nil
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -104,24 +165,26 @@ function ModeSelectScene:changeOption(rel)
|
|||||||
elseif self.menu_state.select == "ruleset" then
|
elseif self.menu_state.select == "ruleset" then
|
||||||
self:changeRuleset(rel)
|
self:changeRuleset(rel)
|
||||||
end
|
end
|
||||||
|
playSE("cursor")
|
||||||
end
|
end
|
||||||
|
|
||||||
function ModeSelectScene:switchSelect(rel)
|
function ModeSelectScene:switchSelect()
|
||||||
if self.menu_state.select == "mode" then
|
if self.menu_state.select == "mode" then
|
||||||
self.menu_state.select = "ruleset"
|
self.menu_state.select = "ruleset"
|
||||||
elseif self.menu_state.select == "ruleset" then
|
elseif self.menu_state.select == "ruleset" then
|
||||||
self.menu_state.select = "mode"
|
self.menu_state.select = "mode"
|
||||||
end
|
end
|
||||||
|
playSE("cursor_lr")
|
||||||
end
|
end
|
||||||
|
|
||||||
function ModeSelectScene:changeMode(rel)
|
function ModeSelectScene:changeMode(rel)
|
||||||
local len = table.getn(game_modes)
|
local len = table.getn(game_modes)
|
||||||
self.menu_state.mode = (self.menu_state.mode + len + rel - 1) % len + 1
|
self.menu_state.mode = Mod1(self.menu_state.mode + rel, len)
|
||||||
end
|
end
|
||||||
|
|
||||||
function ModeSelectScene:changeRuleset(rel)
|
function ModeSelectScene:changeRuleset(rel)
|
||||||
local len = table.getn(rulesets)
|
local len = table.getn(rulesets)
|
||||||
self.menu_state.ruleset = (self.menu_state.ruleset + len + rel - 1) % len + 1
|
self.menu_state.ruleset = Mod1(self.menu_state.ruleset + rel, len)
|
||||||
end
|
end
|
||||||
|
|
||||||
return ModeSelectScene
|
return ModeSelectScene
|
||||||
|
|||||||
@@ -349,7 +349,7 @@ function Grid:markSquares()
|
|||||||
elseif i == 2 then
|
elseif i == 2 then
|
||||||
for j = 0, 3 do
|
for j = 0, 3 do
|
||||||
for k = 0, 3 do
|
for k = 0, 3 do
|
||||||
self.grid[y+j][x+k].colour = "F"
|
self.grid[y+j][x+k].colour = "W"
|
||||||
self.grid[y+j][x+k].skin = "square"
|
self.grid[y+j][x+k].skin = "square"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
@@ -126,9 +126,6 @@ function GameMode:update(inputs, ruleset)
|
|||||||
if inputs["left"] or inputs["right"] then
|
if inputs["left"] or inputs["right"] then
|
||||||
inputs["up"] = false
|
inputs["up"] = false
|
||||||
inputs["down"] = false
|
inputs["down"] = false
|
||||||
elseif inputs["up"] or inputs["down"] then
|
|
||||||
inputs["left"] = false
|
|
||||||
inputs["right"] = false
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -490,20 +487,15 @@ end
|
|||||||
|
|
||||||
function GameMode:initializeOrHold(inputs, ruleset)
|
function GameMode:initializeOrHold(inputs, ruleset)
|
||||||
if (
|
if (
|
||||||
(self.frames == 0 or (ruleset.are and self:getARE() ~= 0)) and self.ihs or false
|
(self.frames == 0 or (ruleset.are and self:getARE() ~= 0))
|
||||||
|
and self.ihs or false
|
||||||
) and self.enable_hold and inputs["hold"] == true then
|
) and self.enable_hold and inputs["hold"] == true then
|
||||||
self:hold(inputs, ruleset, true)
|
self:hold(inputs, ruleset, true)
|
||||||
else
|
else
|
||||||
self:initializeNextPiece(inputs, ruleset, self.next_queue[1])
|
self:initializeNextPiece(inputs, ruleset, self.next_queue[1])
|
||||||
end
|
end
|
||||||
self:onPieceEnter()
|
self:onPieceEnter()
|
||||||
if not self.grid:canPlacePiece(self.piece) then
|
self:onEnterOrHold(inputs, ruleset)
|
||||||
self.game_over = true
|
|
||||||
end
|
|
||||||
ruleset:dropPiece(
|
|
||||||
inputs, self.piece, self.grid, self:getGravity(),
|
|
||||||
self:getDropSpeed(), self.drop_locked, self.hard_drop_locked
|
|
||||||
)
|
|
||||||
end
|
end
|
||||||
|
|
||||||
function GameMode:hold(inputs, ruleset, ihs)
|
function GameMode:hold(inputs, ruleset, ihs)
|
||||||
@@ -516,7 +508,7 @@ function GameMode:hold(inputs, ruleset, ihs)
|
|||||||
self.hold_queue = {
|
self.hold_queue = {
|
||||||
skin = self.piece.skin,
|
skin = self.piece.skin,
|
||||||
shape = self.piece.shape,
|
shape = self.piece.shape,
|
||||||
orientation = ruleset:getDefaultOrientation(),
|
orientation = ruleset:getDefaultOrientation(self.piece.shape),
|
||||||
}
|
}
|
||||||
end
|
end
|
||||||
if data == nil then
|
if data == nil then
|
||||||
@@ -525,21 +517,35 @@ function GameMode:hold(inputs, ruleset, ihs)
|
|||||||
self:initializeNextPiece(inputs, ruleset, data, false)
|
self:initializeNextPiece(inputs, ruleset, data, false)
|
||||||
end
|
end
|
||||||
self.held = true
|
self.held = true
|
||||||
if ihs then playSE("ihs")
|
|
||||||
else playSE("hold") end
|
|
||||||
self:onHold()
|
self:onHold()
|
||||||
if not self.grid:canPlacePiece(self.piece) then
|
if ihs then
|
||||||
self.game_over = true
|
playSE("ihs")
|
||||||
|
else
|
||||||
|
playSE("hold")
|
||||||
|
self:onEnterOrHold(inputs, ruleset)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
function GameMode:initializeNextPiece(inputs, ruleset, piece_data, generate_next_piece)
|
function GameMode:onEnterOrHold(inputs, ruleset)
|
||||||
if not self.buffer_soft_drop and self.lock_drop or (
|
if not self.grid:canPlacePiece(self.piece) then
|
||||||
|
self.game_over = true
|
||||||
|
return
|
||||||
|
end
|
||||||
|
ruleset:dropPiece(
|
||||||
|
inputs, self.piece, self.grid, self:getGravity(),
|
||||||
|
self:getDropSpeed(), self.drop_locked, self.hard_drop_locked
|
||||||
|
)
|
||||||
|
end
|
||||||
|
|
||||||
|
function GameMode:initializeNextPiece(
|
||||||
|
inputs, ruleset, piece_data, generate_next_piece
|
||||||
|
)
|
||||||
|
if not inputs.hold and not self.buffer_soft_drop and self.lock_drop or (
|
||||||
not ruleset.are or self:getARE() == 0
|
not ruleset.are or self:getARE() == 0
|
||||||
) then
|
) then
|
||||||
self.drop_locked = true
|
self.drop_locked = true
|
||||||
end
|
end
|
||||||
if not self.buffer_hard_drop and self.lock_hard_drop or (
|
if not inputs.hold and not self.buffer_hard_drop and self.lock_hard_drop or (
|
||||||
not ruleset.are or self:getARE() == 0
|
not ruleset.are or self:getARE() == 0
|
||||||
) then
|
) then
|
||||||
self.hard_drop_locked = true
|
self.hard_drop_locked = true
|
||||||
@@ -683,7 +689,9 @@ function GameMode:drawPiece()
|
|||||||
end
|
end
|
||||||
|
|
||||||
function GameMode:drawGhostPiece(ruleset)
|
function GameMode:drawGhostPiece(ruleset)
|
||||||
if self.piece == nil then return end
|
if self.piece == nil or not self.grid:canPlacePiece(self.piece) then
|
||||||
|
return
|
||||||
|
end
|
||||||
local ghost_piece = self.piece:withOffset({x=0, y=0})
|
local ghost_piece = self.piece:withOffset({x=0, y=0})
|
||||||
ghost_piece.ghost = true
|
ghost_piece.ghost = true
|
||||||
ghost_piece:dropToBottom(self.grid)
|
ghost_piece:dropToBottom(self.grid)
|
||||||
@@ -853,15 +861,7 @@ function GameMode:drawFrame()
|
|||||||
-- game frame
|
-- game frame
|
||||||
if self.grid.width == 10 and self.grid.height == 24 then
|
if self.grid.width == 10 and self.grid.height == 24 then
|
||||||
love.graphics.draw(misc_graphics["frame"], 48, 64)
|
love.graphics.draw(misc_graphics["frame"], 48, 64)
|
||||||
end
|
else
|
||||||
|
|
||||||
love.graphics.setColor(0, 0, 0, 200)
|
|
||||||
love.graphics.rectangle(
|
|
||||||
"fill", 64, 80,
|
|
||||||
16 * self.grid.width, 16 * (self.grid.height - 4)
|
|
||||||
)
|
|
||||||
|
|
||||||
if self.grid.width ~= 10 or self.grid.height ~= 24 then
|
|
||||||
love.graphics.setColor(174/255, 83/255, 76/255, 1)
|
love.graphics.setColor(174/255, 83/255, 76/255, 1)
|
||||||
love.graphics.setLineWidth(8)
|
love.graphics.setLineWidth(8)
|
||||||
love.graphics.line(
|
love.graphics.line(
|
||||||
@@ -881,6 +881,11 @@ function GameMode:drawFrame()
|
|||||||
60,76
|
60,76
|
||||||
)
|
)
|
||||||
love.graphics.setLineWidth(1)
|
love.graphics.setLineWidth(1)
|
||||||
|
love.graphics.setColor(0, 0, 0, 200)
|
||||||
|
love.graphics.rectangle(
|
||||||
|
"fill", 64, 80,
|
||||||
|
16 * self.grid.width, 16 * (self.grid.height - 4)
|
||||||
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -897,7 +902,20 @@ end
|
|||||||
|
|
||||||
function GameMode:drawCustom() end
|
function GameMode:drawCustom() end
|
||||||
|
|
||||||
|
function GameMode:drawIfPaused()
|
||||||
|
love.graphics.setFont(font_3x5_3)
|
||||||
|
love.graphics.printf("GAME PAUSED!", 64, 160, 160, "center")
|
||||||
|
end
|
||||||
|
|
||||||
|
-- transforms specified in here will transform the whole screen
|
||||||
|
-- if you want a transform for a particular component, push the
|
||||||
|
-- default transform by using love.graphics.push(), do your
|
||||||
|
-- transform, and then love.graphics.pop() at the end of that
|
||||||
|
-- component's draw call!
|
||||||
|
function GameMode:transformScreen() end
|
||||||
|
|
||||||
function GameMode:draw(paused)
|
function GameMode:draw(paused)
|
||||||
|
self:transformScreen()
|
||||||
self:drawBackground()
|
self:drawBackground()
|
||||||
self:drawFrame()
|
self:drawFrame()
|
||||||
self:drawGrid()
|
self:drawGrid()
|
||||||
@@ -919,9 +937,8 @@ function GameMode:draw(paused)
|
|||||||
)
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
love.graphics.setFont(font_3x5_3)
|
|
||||||
if paused then
|
if paused then
|
||||||
love.graphics.printf("GAME PAUSED!", 64, 160, 160, "center")
|
self:drawIfPaused()
|
||||||
end
|
end
|
||||||
|
|
||||||
if self.completed then
|
if self.completed then
|
||||||
|
|||||||
@@ -290,10 +290,10 @@ function Marathon2020Game:sectionPassed(old_level, new_level)
|
|||||||
end
|
end
|
||||||
|
|
||||||
function Marathon2020Game:checkTorikan(section)
|
function Marathon2020Game:checkTorikan(section)
|
||||||
if section == 5 and self.frames < frameTime(6,00,00) then self.torikan_passed[500] = true end
|
if section == 5 and self.frames < frameTime(8,00,00) then self.torikan_passed[500] = true end
|
||||||
if section == 9 and self.frames < frameTime(8,30,00) then self.torikan_passed[900] = true end
|
if section == 9 and self.frames < frameTime(10,30,00) then self.torikan_passed[900] = true end
|
||||||
if section == 10 and self.frames < frameTime(8,45,00) then self.torikan_passed[1000] = true end
|
if section == 10 and self.frames < frameTime(10,45,00) then self.torikan_passed[1000] = true end
|
||||||
if section == 15 and self.frames < frameTime(11,30,00) then self.torikan_passed[1500] = true end
|
if section == 15 and self.frames < frameTime(12,30,00) then self.torikan_passed[1500] = true end
|
||||||
if section == 19 and self.frames < frameTime(13,15,00) then self.torikan_passed[1900] = true end
|
if section == 19 and self.frames < frameTime(13,15,00) then self.torikan_passed[1900] = true end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -354,7 +354,7 @@ function Marathon2020Game:updateSectionTimes(old_level, new_level)
|
|||||||
|
|
||||||
if (
|
if (
|
||||||
self.section_status[section - 1] == "cool" and
|
self.section_status[section - 1] == "cool" and
|
||||||
self.secondary_section_times[section] < self.secondary_section_times[section - 1] + 120 and
|
self.secondary_section_times[section] <= self.secondary_section_times[section - 1] + 120 and
|
||||||
self.secondary_section_times[section] < cool_cutoffs[self.delay_level]
|
self.secondary_section_times[section] < cool_cutoffs[self.delay_level]
|
||||||
) then
|
) then
|
||||||
sectionCool(section)
|
sectionCool(section)
|
||||||
@@ -407,11 +407,12 @@ GM-roll requirements
|
|||||||
You qualify for the GM roll if you:
|
You qualify for the GM roll if you:
|
||||||
- Reach level 2020
|
- Reach level 2020
|
||||||
- with a grade of 50
|
- with a grade of 50
|
||||||
|
- and at least 25,000 grade points
|
||||||
- in less than 13:30.00 total.
|
- in less than 13:30.00 total.
|
||||||
|
|
||||||
]]--
|
]]--
|
||||||
|
|
||||||
return self.level >= 2020 and self:getTotalGrade() == 50 and self.frames <= frameTime(13,30)
|
return self.level >= 2020 and self:getTotalGrade() == 50 and self.grade_points >= 25000 and self.frames <= frameTime(13,30)
|
||||||
end
|
end
|
||||||
|
|
||||||
function Marathon2020Game:drawGrid()
|
function Marathon2020Game:drawGrid()
|
||||||
|
|||||||
@@ -218,16 +218,11 @@ function MarathonA3Game:updateSectionTimes(old_level, new_level)
|
|||||||
section_70_time = self.frames - self.section_start_time
|
section_70_time = self.frames - self.section_start_time
|
||||||
table.insert(self.secondary_section_times, section_70_time)
|
table.insert(self.secondary_section_times, section_70_time)
|
||||||
|
|
||||||
if section <= 9 and self.section_status[section - 1] == "cool" and
|
if section <= 9 and self.secondary_section_times[section] < cool_cutoffs[section] and
|
||||||
self.secondary_section_times[section] < self.secondary_section_times[section - 1] + 120 then
|
(section == 1 or self.secondary_section_times[section] <= self.secondary_section_times[section - 1] + 120) then
|
||||||
self.section_cool = true
|
self.section_cool = true
|
||||||
self.coolregret_message = "COOL!!"
|
self.coolregret_message = "COOL!!"
|
||||||
self.coolregret_timer = 300
|
self.coolregret_timer = 300
|
||||||
elseif self.section_status[section - 1] == "cool" then self.section_cool = false
|
|
||||||
elseif section <= 9 and self.secondary_section_times[section] < cool_cutoffs[section] then
|
|
||||||
self.section_cool = true
|
|
||||||
self.coolregret_message = "COOL!!"
|
|
||||||
self.coolregret_timer = 300
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -41,7 +41,7 @@ function PhantomManiaGame:getARE()
|
|||||||
end
|
end
|
||||||
|
|
||||||
function PhantomManiaGame:getLineARE()
|
function PhantomManiaGame:getLineARE()
|
||||||
if self.level < 100 then return 18
|
if self.level < 100 then return 14
|
||||||
elseif self.level < 400 then return 8
|
elseif self.level < 400 then return 8
|
||||||
elseif self.level < 500 then return 7
|
elseif self.level < 500 then return 7
|
||||||
else return 6 end
|
else return 6 end
|
||||||
|
|||||||
@@ -179,7 +179,7 @@ function PhantomMania2Game:onPieceLock(piece, cleared_row_count)
|
|||||||
end
|
end
|
||||||
|
|
||||||
function PhantomMania2Game:onHold()
|
function PhantomMania2Game:onHold()
|
||||||
self.super.onHold()
|
self.super:onHold()
|
||||||
self.hold_age = 0
|
self.hold_age = 0
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -287,7 +287,8 @@ function PhantomMania2Game:setHoldOpacity()
|
|||||||
if self.level > 1000 and self.level < 1300 then
|
if self.level > 1000 and self.level < 1300 then
|
||||||
love.graphics.setColor(1, 1, 1, 1 - math.min(1, self.hold_age / 15))
|
love.graphics.setColor(1, 1, 1, 1 - math.min(1, self.hold_age / 15))
|
||||||
else
|
else
|
||||||
self.super:setHoldOpacity(1, self.held and 0.6 or 1)
|
local colour = self.held and 0.6 or 1
|
||||||
|
love.graphics.setColor(colour, colour, colour, 1)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
@@ -97,14 +97,13 @@ end
|
|||||||
function SurvivalA2Game:onLineClear(cleared_row_count)
|
function SurvivalA2Game:onLineClear(cleared_row_count)
|
||||||
if not self.clear then
|
if not self.clear then
|
||||||
local new_level = math.min(self.level + cleared_row_count, 999)
|
local new_level = math.min(self.level + cleared_row_count, 999)
|
||||||
if self.level == 999 or self:hitTorikan(self.level, new_level) then
|
if new_level == 999 or self:hitTorikan(self.level, new_level) then
|
||||||
self.clear = true
|
self.clear = true
|
||||||
if self.level < 999 then
|
if new_level < 999 then
|
||||||
self.game_over = true
|
self.game_over = true
|
||||||
end
|
end
|
||||||
else
|
|
||||||
self.level = new_level
|
|
||||||
end
|
end
|
||||||
|
self.level = new_level
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -158,7 +157,7 @@ function SurvivalA2Game:drawScoringInfo()
|
|||||||
|
|
||||||
love.graphics.setFont(font_3x5_3)
|
love.graphics.setFont(font_3x5_3)
|
||||||
love.graphics.printf(self.score, text_x, 220, 90, "left")
|
love.graphics.printf(self.score, text_x, 220, 90, "left")
|
||||||
if self.roll_frames > 2968 then love.graphics.setColor(1, 0.5, 0, 1)
|
if self.roll_frames > 1800 then love.graphics.setColor(1, 0.5, 0, 1)
|
||||||
elseif self.level >= 999 and self.clear then love.graphics.setColor(0, 1, 0, 1) end
|
elseif self.level >= 999 and self.clear then love.graphics.setColor(0, 1, 0, 1) end
|
||||||
if self:getLetterGrade() ~= "" then love.graphics.printf(self:getLetterGrade(), text_x, 140, 90, "left") end
|
if self:getLetterGrade() ~= "" then love.graphics.printf(self:getLetterGrade(), text_x, 140, 90, "left") end
|
||||||
love.graphics.setColor(1, 1, 1, 1)
|
love.graphics.setColor(1, 1, 1, 1)
|
||||||
|
|||||||
@@ -47,18 +47,11 @@ function Ruleset:new(game_mode)
|
|||||||
else
|
else
|
||||||
bones = config.gamesettings.piece_colour == 3 and "w" or ""
|
bones = config.gamesettings.piece_colour == 3 and "w" or ""
|
||||||
end
|
end
|
||||||
blocks.bone = {
|
for colour in pairs(blocks["2tie"]) do
|
||||||
R = love.graphics.newImage("res/img/bone" .. bones .. ".png"),
|
blocks.bone[colour] = love.graphics.newImage(
|
||||||
O = love.graphics.newImage("res/img/bone" .. bones .. ".png"),
|
"res/img/bone" .. bones .. ".png"
|
||||||
Y = love.graphics.newImage("res/img/bone" .. bones .. ".png"),
|
)
|
||||||
G = love.graphics.newImage("res/img/bone" .. bones .. ".png"),
|
end
|
||||||
C = love.graphics.newImage("res/img/bone" .. bones .. ".png"),
|
|
||||||
B = love.graphics.newImage("res/img/bone" .. bones .. ".png"),
|
|
||||||
M = love.graphics.newImage("res/img/bone" .. bones .. ".png"),
|
|
||||||
F = love.graphics.newImage("res/img/bone" .. bones .. ".png"),
|
|
||||||
A = love.graphics.newImage("res/img/bone" .. bones .. ".png"),
|
|
||||||
X = love.graphics.newImage("res/img/bone" .. bones .. ".png"),
|
|
||||||
}
|
|
||||||
end
|
end
|
||||||
|
|
||||||
function Ruleset:rotatePiece(inputs, piece, grid, prev_inputs, initial)
|
function Ruleset:rotatePiece(inputs, piece, grid, prev_inputs, initial)
|
||||||
@@ -162,18 +155,18 @@ function Ruleset:dropPiece(
|
|||||||
hard_drop_enabled, additive_gravity, classic_lock
|
hard_drop_enabled, additive_gravity, classic_lock
|
||||||
)
|
)
|
||||||
local y = piece.position.y
|
local y = piece.position.y
|
||||||
if inputs["down"] == true and drop_locked == false then
|
if inputs["up"] == true and hard_drop_enabled == true then
|
||||||
if additive_gravity then
|
|
||||||
piece:addGravity(gravity + drop_speed, grid, classic_lock)
|
|
||||||
else
|
|
||||||
piece:addGravity(math.max(gravity, drop_speed), grid, classic_lock)
|
|
||||||
end
|
|
||||||
elseif inputs["up"] == true and hard_drop_enabled == true then
|
|
||||||
if hard_drop_locked == true or piece:isDropBlocked(grid) then
|
if hard_drop_locked == true or piece:isDropBlocked(grid) then
|
||||||
piece:addGravity(gravity, grid, classic_lock)
|
piece:addGravity(gravity, grid, classic_lock)
|
||||||
else
|
else
|
||||||
piece:dropToBottom(grid)
|
piece:dropToBottom(grid)
|
||||||
end
|
end
|
||||||
|
elseif inputs["down"] == true and drop_locked == false then
|
||||||
|
if additive_gravity then
|
||||||
|
piece:addGravity(gravity + drop_speed, grid, classic_lock)
|
||||||
|
else
|
||||||
|
piece:addGravity(math.max(gravity, drop_speed), grid, classic_lock)
|
||||||
|
end
|
||||||
else
|
else
|
||||||
piece:addGravity(gravity, grid, classic_lock)
|
piece:addGravity(gravity, grid, classic_lock)
|
||||||
end
|
end
|
||||||
@@ -221,7 +214,7 @@ function Ruleset:initializePiece(
|
|||||||
colours = self.colourscheme
|
colours = self.colourscheme
|
||||||
end
|
end
|
||||||
|
|
||||||
local spawn_x = math.floor(spawn_positions[data.shape].x / 10 * grid.width)
|
local spawn_x = math.floor(spawn_positions[data.shape].x * grid.width / 10)
|
||||||
|
|
||||||
local spawn_dy
|
local spawn_dy
|
||||||
if (config.gamesettings.spawn_positions == 1) then
|
if (config.gamesettings.spawn_positions == 1) then
|
||||||
@@ -237,7 +230,7 @@ function Ruleset:initializePiece(
|
|||||||
end
|
end
|
||||||
|
|
||||||
local piece = Piece(data.shape, data.orientation - 1, {
|
local piece = Piece(data.shape, data.orientation - 1, {
|
||||||
x = spawn_x or spawn_positions[data.shape].x,
|
x = spawn_x,
|
||||||
y = spawn_positions[data.shape].y - spawn_dy
|
y = spawn_positions[data.shape].y - spawn_dy
|
||||||
}, self.block_offsets, 0, 0, data.skin, colours[data.shape], big)
|
}, self.block_offsets, 0, 0, data.skin, colours[data.shape], big)
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user