diff --git a/CHANGELOG.md b/CHANGELOG.md
index 875bc46..7b599ea 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,16 +1,32 @@
# Changelog
All notable changes will be documented in this file.
-## [1.1.0]
-### Added
-- 32bit support
-- Controller (dancepads) support
-- Pause screen
-- Main Menu overhaul
-- Cool intro screen thing
-- Uh lots of bullshit
-- Remind me to actually add this later lmaooo
+The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
+and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
-## [1.0.0] - 2020-10-05
+## [Unreleased]
+### Added
+
+
+## [0.2.1] - 2020-11-06
+### Added
+- Scores to the freeplay menu
+- A few new intro boot messages.
+- Lightning effect in Spooky stages
+- Campaign scores, can now compete on scoreboards for campaign!
+- Can now change difficulties in
+
+### Changed
+- Balanced out Normal mode for all songs. Should be much easier all around.
+- Put tutorial in it's own 'week', so that if you want to play week 1, you don't have to play the tutorial.
+
+### Fixed
+- One of the charting bits on South and Spookeez during the intro.
+
+## [0.2.0] - 2020-11-01
+### Added
+- Uhh Newgrounds release lolol I always lose track of shit.
+
+## [0.1.0] - 2020-10-05
### Added
- Uh, everything. This the game's initial gamejam release. We put it out
\ No newline at end of file
diff --git a/Project.xml b/Project.xml
index d7c38fa..673afa4 100644
--- a/Project.xml
+++ b/Project.xml
@@ -2,7 +2,7 @@
-
+
@@ -44,6 +44,8 @@
+
+
@@ -57,6 +59,9 @@
+
+
+
@@ -98,8 +103,8 @@
-
-
+
+
diff --git a/assets/data/dadbattle/dadbattle.json b/assets/data/dadbattle/dadbattle.json
index a496d54..dd800cd 100644
--- a/assets/data/dadbattle/dadbattle.json
+++ b/assets/data/dadbattle/dadbattle.json
@@ -1 +1 @@
-{"song":{"song":"Dadbattle","bpm":180,"sections":45,"notes":[{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[10667,2,0],[11000,0,0],[11167,1,0],[11333,2,0],[11750,0,0],[11833,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[12000,2,0],[12167,3,0],[12333,0,0],[12500,1,0],[12667,2,0],[13083,0,0],[13250,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[13333.666666666666,2,0],[13666.666666666666,0,0],[13833.666666666666,1,0],[13999.666666666666,2,0],[14416.666666666666,0,0],[14499.666666666666,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[14666.666666666666,2,0],[14833.666666666666,3,0],[14999.666666666666,0,0],[15166.666666666666,1,0],[15333.666666666666,2,0],[15749.666666666666,0,0],[15916.666666666666,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[16000,1,0],[16333,0,0],[16500,3,0],[16667,1,0],[16917,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[17348,1,0],[17750,0,0],[17917,0,0],[18083,3,0],[18250,3,0],[18417,3,0],[18583,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[18666.666666666668,1,0],[18999.666666666668,0,0],[19166.666666666668,3,0],[19333.666666666668,1,0],[19583.666666666668,2,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[20014.666666666668,1,0],[20416.666666666668,0,0],[20583.666666666668,0,0],[20749.666666666668,3,0],[20916.666666666668,3,0],[21083.666666666668,3,0],[21249.666666666668,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[21750,2,0],[21917,1,0],[22083,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[22833,1,0],[23000,3,0],[23250,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[24417,2,0],[24750,1,0],[25000,0,0],[25167,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[25342,2,0],[25500,3,0],[25583,0,0],[25750,1,0],[25917,3,0],[26083,2,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[27083.333333333332,2,0],[27250.333333333332,1,0],[27416.333333333332,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[28166.333333333332,1,0],[28333.333333333332,3,0],[28583.333333333332,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[29750.333333333332,2,0],[30083.333333333332,1,0],[30333.333333333332,0,0],[30500.333333333332,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[30675.333333333332,2,0],[30833.333333333332,3,0],[30916.333333333332,0,0],[31083.333333333332,1,0],[31250.333333333332,3,0],[31416.333333333332,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[32167,0,0],[32333,3,0],[32500,2,0],[32750,1,0],[33000,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[33500,2,0],[33667,3,0],[33833,1,0],[34083,2,0],[34417,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[34669,0,0],[35000,1,0],[35333,3,0],[35667,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[36008,2,0],[36333,3,0],[36750,0,0],[36750,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[37583,1,0],[37750,3,0],[37917,2,0],[38083,0,0],[38167,2,0],[38333,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[38679,0,0],[38750,3,0],[38833,0,0],[39000,1,0],[39167,0,0],[39333,2,0],[39500,3,0],[39667,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[40167,0,0],[40333,3,0],[40500,1,0],[40750,2,0],[40917,3,0],[41083,1,0],[41250,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[41337,4,0],[41750,6,0],[41583,5,0],[41917,7,0],[42083,6,0],[42250,5,0],[42417,4,0],[42583,5,0],[41348,0,0],[41583,1,0],[41750,0,0],[41917,3,0],[42167,2,0],[42333,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[42833.666666666664,0,0],[42999.666666666664,3,0],[43166.666666666664,2,0],[43416.666666666664,1,0],[43666.666666666664,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[44166.666666666664,2,0],[44333.666666666664,3,0],[44499.666666666664,1,0],[44749.666666666664,2,0],[45083.666666666664,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[45335.666666666664,0,0],[45666.666666666664,1,0],[45999.666666666664,3,0],[46333.666666666664,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[46674.666666666664,2,0],[46999.666666666664,3,0],[47416.666666666664,0,0],[47416.666666666664,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[48249.666666666664,1,0],[48416.666666666664,3,0],[48583.666666666664,2,0],[48749.666666666664,0,0],[48833.666666666664,2,0],[48999.666666666664,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[49345.666666666664,0,0],[49416.666666666664,3,0],[49499.666666666664,0,0],[49666.666666666664,1,0],[49833.666666666664,0,0],[49999.666666666664,2,0],[50166.666666666664,3,0],[50333.666666666664,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[50833.666666666664,0,0],[50999.666666666664,3,0],[51166.666666666664,1,0],[51416.666666666664,2,0],[51583.666666666664,3,0],[51749.666666666664,1,0],[51916.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[52014.666666666664,0,0],[52250,0,0],[52417,2,0],[52583,2,0],[52750,3,0],[53000,1,0],[53000,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[53333.666666666664,2,0],[53666.666666666664,0,0],[53833.666666666664,1,0],[53999.666666666664,2,0],[54416.666666666664,0,0],[54499.666666666664,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[54666.666666666664,2,0],[54833.666666666664,3,0],[54999.666666666664,0,0],[55166.666666666664,1,0],[55333.666666666664,2,0],[55749.666666666664,0,0],[55916.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[56000.33333333333,2,0],[56333.33333333333,0,0],[56500.33333333333,1,0],[56666.33333333333,2,0],[57083.33333333333,0,0],[57166.33333333333,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[57333.33333333333,2,0],[57500.33333333333,3,0],[57666.33333333333,0,0],[57833.33333333333,1,0],[58000.33333333333,2,0],[58416.33333333333,0,0],[58583.33333333333,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[58666.666666666664,1,0],[58999.666666666664,0,0],[59166.666666666664,3,0],[59333.666666666664,1,0],[59583.666666666664,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[60014.666666666664,1,0],[60416.666666666664,0,0],[60583.666666666664,0,0],[60749.666666666664,3,0],[60916.666666666664,3,0],[61083.666666666664,3,0],[61249.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[61333.33333333333,1,0],[61666.33333333333,0,0],[61833.33333333333,3,0],[62000.33333333333,1,0],[62250.33333333333,2,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[62681.33333333333,1,0],[63083.33333333333,0,0],[63250.33333333333,0,0],[63416.33333333333,3,0],[63583.33333333333,3,0],[63750.33333333333,3,0],[63916.33333333333,3,0],[62667,4,0],[62833,5,0],[63000,6,0],[63167,7,0],[63333,6,0],[63500,5,0],[63667,4,0],[63833,5,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[64416.666666666664,2,0],[64583.666666666664,1,0],[64749.666666666664,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[65499.666666666664,1,0],[65666.66666666666,3,0],[65916.66666666666,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[67083.66666666666,2,0],[67416.66666666666,1,0],[67666.66666666666,0,0],[67833.66666666666,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[68008.66666666666,2,0],[68166.66666666666,3,0],[68249.66666666666,0,0],[68416.66666666666,1,0],[68583.66666666666,3,0],[68749.66666666666,2,0],[68000,4,0],[68167,5,0],[68333,6,0],[68500,7,0],[68667,6,0],[68833,5,0],[69000,4,0],[69167,5,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[69750,2,0],[69917,1,0],[70083,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[70833,1,0],[71000,3,0],[71250,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[72417,2,0],[72750,1,0],[73000,0,0],[73167,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[73342,2,0],[73500,3,0],[73583,0,0],[73750,1,0],[73917,3,0],[74083,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[74667,2,0],[75000,0,0],[75167,1,0],[75333,2,0],[75750,0,0],[75833,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[76000,2,0],[76167,3,0],[76333,0,0],[76500,1,0],[76667,2,0],[77000,2,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[77333.66666666667,2,0],[77666.66666666667,0,0],[77833.66666666667,1,0],[77999.66666666667,2,0],[78416.66666666667,0,0],[78499.66666666667,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[78666.66666666667,2,0],[78833.66666666667,3,0],[78999.66666666667,0,0],[79166.66666666667,1,0],[79333.66666666667,2,0],[79666.66666666667,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[80000,1,0],[80333,0,0],[80500,3,0],[80667,1,0],[80917,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[81348,1,0],[81667,1,0],[82000,1,0]]},{"lengthInSteps":16,"bpm":180,"changeBPM":false,"mustHitSection":true,"sectionNotes":[[82666.66666666667,1,0],[82999.66666666667,0,0],[83166.66666666667,3,0],[83333.66666666667,1,0],[83583.66666666667,2,0]],"typeOfSection":0},{"lengthInSteps":16,"bpm":180,"changeBPM":false,"mustHitSection":true,"sectionNotes":[[84014.66666666667,1,0],[84333.66666666667,1,0],[84666.66666666667,1,0]],"typeOfSection":0}],"needsVoices":true,"speed":1.9000000000000004,"player1":"bf","player2":"dad"},"bpm":180,"sections":64,"notes":[{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[10667,2,0],[11000,0,0],[11167,1,0],[11333,2,0],[11750,0,0],[11833,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[12000,2,0],[12167,3,0],[12333,0,0],[12500,1,0],[12667,2,0],[13083,0,0],[13250,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[13333.666666666666,2,0],[13666.666666666666,0,0],[13833.666666666666,1,0],[13999.666666666666,2,0],[14416.666666666666,0,0],[14499.666666666666,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[14666.666666666666,2,0],[14833.666666666666,3,0],[14999.666666666666,0,0],[15166.666666666666,1,0],[15333.666666666666,2,0],[15749.666666666666,0,0],[15916.666666666666,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[16000,1,0],[16333,0,0],[16500,3,0],[16667,1,0],[16917,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[17348,1,0],[17750,0,0],[17917,0,0],[18083,3,0],[18250,3,0],[18417,3,0],[18583,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[18666.666666666668,1,0],[18999.666666666668,0,0],[19166.666666666668,3,0],[19333.666666666668,1,0],[19583.666666666668,2,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[20014.666666666668,1,0],[20416.666666666668,0,0],[20583.666666666668,0,0],[20749.666666666668,3,0],[20916.666666666668,3,0],[21083.666666666668,3,0],[21249.666666666668,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[21750,2,0],[21917,1,0],[22083,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[22833,1,0],[23000,3,0],[23250,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[24417,2,0],[24750,1,0],[25000,0,0],[25167,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[25342,2,0],[25500,3,0],[25583,0,0],[25750,1,0],[25917,3,0],[26083,2,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[27083.333333333332,2,0],[27250.333333333332,1,0],[27416.333333333332,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[28166.333333333332,1,0],[28333.333333333332,3,0],[28583.333333333332,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[29750.333333333332,2,0],[30083.333333333332,1,0],[30333.333333333332,0,0],[30500.333333333332,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[30675.333333333332,2,0],[30833.333333333332,3,0],[30916.333333333332,0,0],[31083.333333333332,1,0],[31250.333333333332,3,0],[31416.333333333332,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[32167,0,0],[32333,3,0],[32500,2,0],[32750,1,0],[33000,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[33500,2,0],[33667,3,0],[33833,1,0],[34083,2,0],[34417,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[34669,0,0],[35000,1,0],[35333,3,0],[35667,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[36008,2,0],[36333,3,0],[36750,0,0],[36750,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[37583,1,0],[37750,3,0],[37917,2,0],[38083,0,0],[38167,2,0],[38333,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[38679,0,0],[38750,3,0],[38833,0,0],[39000,1,0],[39167,0,0],[39333,2,0],[39500,3,0],[39667,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[40167,0,0],[40333,3,0],[40500,1,0],[40750,2,0],[40917,3,0],[41083,1,0],[41250,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[41337,4,0],[41750,6,0],[41583,5,0],[41917,7,0],[42083,6,0],[42250,5,0],[42417,4,0],[42583,5,0],[41348,0,0],[41583,1,0],[41750,0,0],[41917,3,0],[42167,2,0],[42333,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[42833.666666666664,0,0],[42999.666666666664,3,0],[43166.666666666664,2,0],[43416.666666666664,1,0],[43666.666666666664,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[44166.666666666664,2,0],[44333.666666666664,3,0],[44499.666666666664,1,0],[44749.666666666664,2,0],[45083.666666666664,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[45335.666666666664,0,0],[45666.666666666664,1,0],[45999.666666666664,3,0],[46333.666666666664,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[46674.666666666664,2,0],[46999.666666666664,3,0],[47416.666666666664,0,0],[47416.666666666664,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[48249.666666666664,1,0],[48416.666666666664,3,0],[48583.666666666664,2,0],[48749.666666666664,0,0],[48833.666666666664,2,0],[48999.666666666664,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[49345.666666666664,0,0],[49416.666666666664,3,0],[49499.666666666664,0,0],[49666.666666666664,1,0],[49833.666666666664,0,0],[49999.666666666664,2,0],[50166.666666666664,3,0],[50333.666666666664,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[50833.666666666664,0,0],[50999.666666666664,3,0],[51166.666666666664,1,0],[51416.666666666664,2,0],[51583.666666666664,3,0],[51749.666666666664,1,0],[51916.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[52014.666666666664,0,0],[52250,0,0],[52417,2,0],[52583,2,0],[52750,3,0],[53000,1,0],[53000,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[53333.666666666664,2,0],[53666.666666666664,0,0],[53833.666666666664,1,0],[53999.666666666664,2,0],[54416.666666666664,0,0],[54499.666666666664,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[54666.666666666664,2,0],[54833.666666666664,3,0],[54999.666666666664,0,0],[55166.666666666664,1,0],[55333.666666666664,2,0],[55749.666666666664,0,0],[55916.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[56000.33333333333,2,0],[56333.33333333333,0,0],[56500.33333333333,1,0],[56666.33333333333,2,0],[57083.33333333333,0,0],[57166.33333333333,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[57333.33333333333,2,0],[57500.33333333333,3,0],[57666.33333333333,0,0],[57833.33333333333,1,0],[58000.33333333333,2,0],[58416.33333333333,0,0],[58583.33333333333,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[58666.666666666664,1,0],[58999.666666666664,0,0],[59166.666666666664,3,0],[59333.666666666664,1,0],[59583.666666666664,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[60014.666666666664,1,0],[60416.666666666664,0,0],[60583.666666666664,0,0],[60749.666666666664,3,0],[60916.666666666664,3,0],[61083.666666666664,3,0],[61249.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[61333.33333333333,1,0],[61666.33333333333,0,0],[61833.33333333333,3,0],[62000.33333333333,1,0],[62250.33333333333,2,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[62681.33333333333,1,0],[63083.33333333333,0,0],[63250.33333333333,0,0],[63416.33333333333,3,0],[63583.33333333333,3,0],[63750.33333333333,3,0],[63916.33333333333,3,0],[62667,4,0],[62833,5,0],[63000,6,0],[63167,7,0],[63333,6,0],[63500,5,0],[63667,4,0],[63833,5,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[64416.666666666664,2,0],[64583.666666666664,1,0],[64749.666666666664,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[65499.666666666664,1,0],[65666.66666666666,3,0],[65916.66666666666,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[67083.66666666666,2,0],[67416.66666666666,1,0],[67666.66666666666,0,0],[67833.66666666666,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[68008.66666666666,2,0],[68166.66666666666,3,0],[68249.66666666666,0,0],[68416.66666666666,1,0],[68583.66666666666,3,0],[68749.66666666666,2,0],[68000,4,0],[68167,5,0],[68333,6,0],[68500,7,0],[68667,6,0],[68833,5,0],[69000,4,0],[69167,5,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[69750,2,0],[69917,1,0],[70083,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[70833,1,0],[71000,3,0],[71250,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[72417,2,0],[72750,1,0],[73000,0,0],[73167,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[73342,2,0],[73500,3,0],[73583,0,0],[73750,1,0],[73917,3,0],[74083,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[74667,2,0],[75000,0,0],[75167,1,0],[75333,2,0],[75750,0,0],[75833,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[76000,2,0],[76167,3,0],[76333,0,0],[76500,1,0],[76667,2,0],[77000,2,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[77333.66666666667,2,0],[77666.66666666667,0,0],[77833.66666666667,1,0],[77999.66666666667,2,0],[78416.66666666667,0,0],[78499.66666666667,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[78666.66666666667,2,0],[78833.66666666667,3,0],[78999.66666666667,0,0],[79166.66666666667,1,0],[79333.66666666667,2,0],[79666.66666666667,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[80000,1,0],[80333,0,0],[80500,3,0],[80667,1,0],[80917,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[81348,1,0],[81667,1,0],[82000,1,0]]},{"lengthInSteps":16,"bpm":180,"changeBPM":false,"mustHitSection":true,"sectionNotes":[[82666.66666666667,1,0],[82999.66666666667,0,0],[83166.66666666667,3,0],[83333.66666666667,1,0],[83583.66666666667,2,0]],"typeOfSection":0},{"lengthInSteps":16,"bpm":180,"changeBPM":false,"mustHitSection":true,"sectionNotes":[[84014.66666666667,1,0],[84333.66666666667,1,0],[84666.66666666667,1,0]],"typeOfSection":0}]}
\ No newline at end of file
+{"song":{"song":"Dadbattle","bpm":180,"sections":45,"notes":[{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[10667,2,0],[11000,0,0],[11333,2,0],[11750,0,0],[11833,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[12000,2,0],[12333,0,0],[12667,2,0],[13083,0,0],[13250,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[13333.666666666666,2,0],[13666.666666666666,0,0],[13999.666666666666,2,0],[14416.666666666666,0,0],[14499.666666666666,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[14666.666666666666,2,0],[14833.666666666666,3,0],[14999.666666666666,0,0],[15333.666666666666,2,0],[15749.666666666666,0,0],[15916.666666666666,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[16000,1,0],[16333,0,0],[16500,3,0],[16667,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[17348,1,0],[17750,0,0],[17917,0,0],[18083,3,0],[18250,3,0],[18417,3,0],[18583,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[18666.666666666668,1,0],[18999.666666666668,0,0],[19166.666666666668,3,0],[19333.666666666668,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[20014.666666666668,1,0],[20416.666666666668,0,0],[20583.666666666668,0,0],[20749.666666666668,3,0],[20916.666666666668,3,0],[21083.666666666668,3,0],[21249.666666666668,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[21750,2,0],[22083,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[22833,1,0],[23000,3,0],[23250,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[24417,2,0],[24750,1,0],[25000,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[25342,2,0],[25583,0,0],[25917,3,0],[26083,2,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[27083.333333333332,2,0],[27416.333333333332,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[28166.333333333332,1,0],[28333.333333333332,3,0],[28583.333333333332,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[29750.333333333332,2,0],[30083.333333333332,1,0],[30333.333333333332,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[30675.333333333332,2,0],[30916.333333333332,0,0],[31250.333333333332,3,0],[31416.333333333332,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[32167,0,0],[32333,3,0],[32500,2,0],[33000,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[33500,2,0],[33667,3,0],[34083,2,0],[34417,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[34669,0,0],[35000,1,0],[35333,3,0],[35667,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[36008,2,0],[36333,3,0],[36750,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[37583,1,0],[38083,0,0],[38333,1,0],[37750,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[38679,0,0],[39167,0,0],[39333,2,0],[39500,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[40167,0,0],[40333,3,0],[40750,2,0],[40917,3,0],[41250,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[41337,4,0],[41750,6,0],[42083,6,0],[42417,4,0],[42583,5,0],[41348,0,0],[41750,0,0],[42167,2,0],[42333,3,0],[41583,1,0],[41917,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[42833.666666666664,0,0],[42999.666666666664,3,0],[43166.666666666664,2,0],[43666.666666666664,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[44166.666666666664,2,0],[44333.666666666664,3,0],[44749.666666666664,2,0],[45083.666666666664,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[45335.666666666664,0,0],[45666.666666666664,1,0],[45999.666666666664,3,0],[46333.666666666664,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[46674.666666666664,2,0],[46999.666666666664,3,0],[47416.666666666664,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[48249.666666666664,1,0],[48749.666666666664,0,0],[48999.666666666664,1,0],[48416.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[49345.666666666664,0,0],[49833.666666666664,0,0],[49999.666666666664,2,0],[50166.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[50833.666666666664,0,0],[50999.666666666664,3,0],[51416.666666666664,2,0],[51583.666666666664,3,0],[51916.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[52014.666666666664,0,0],[52417,2,0],[52750,3,0],[53000,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[53333.666666666664,2,0],[53666.666666666664,0,0],[53999.666666666664,2,0],[54416.666666666664,0,0],[54499.666666666664,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[54666.666666666664,2,0],[54999.666666666664,0,0],[55333.666666666664,2,0],[55749.666666666664,0,0],[55916.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[56000.33333333333,2,0],[56333.33333333333,0,0],[56666.33333333333,2,0],[57083.33333333333,0,0],[57166.33333333333,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[57333.33333333333,2,0],[57500.33333333333,3,0],[57666.33333333333,0,0],[58000.33333333333,2,0],[58416.33333333333,0,0],[58583.33333333333,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[58666.666666666664,1,0],[58999.666666666664,0,0],[59166.666666666664,3,0],[59333.666666666664,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[60014.666666666664,1,0],[60416.666666666664,0,0],[60583.666666666664,0,0],[60749.666666666664,3,0],[60916.666666666664,3,0],[61083.666666666664,3,0],[61249.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[61333.33333333333,1,0],[61666.33333333333,0,0],[61833.33333333333,3,0],[62000.33333333333,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[62681.33333333333,1,0],[63083.33333333333,0,0],[63250.33333333333,0,0],[63416.33333333333,3,0],[63583.33333333333,3,0],[63750.33333333333,3,0],[63916.33333333333,3,0],[62667,4,0],[63000,6,0],[63333,6,0],[63667,4,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[64416.666666666664,2,0],[64583.666666666664,1,0],[64749.666666666664,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[65499.666666666664,1,0],[65666.66666666666,3,0],[65916.66666666666,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[67083.66666666666,2,0],[67416.66666666666,1,0],[67666.66666666666,0,0],[67833.66666666666,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[68008.66666666666,2,0],[68166.66666666666,3,0],[68249.66666666666,0,0],[68416.66666666666,1,0],[68583.66666666666,3,0],[68749.66666666666,2,0],[68000,4,0],[68167,5,0],[68500,7,0],[68833,5,0],[69000,4,0],[69167,5,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[69750,2,0],[69917,1,0],[70083,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[70833,1,0],[71000,3,0],[71250,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[72417,2,0],[72750,1,0],[73000,0,0],[73167,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[73342,2,0],[73583,0,0],[73917,3,0],[74083,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[74667,2,0],[75000,0,0],[75167,1,0],[75750,0,0],[75833,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[76000,2,0],[76333,0,0],[76667,2,0],[77000,2,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[77333.66666666667,2,0],[77666.66666666667,0,0],[77833.66666666667,1,0],[78416.66666666667,0,0],[78499.66666666667,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[78666.66666666667,2,0],[78999.66666666667,0,0],[79333.66666666667,2,0],[79666.66666666667,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[80000,1,0],[80333,0,0],[80500,3,0],[80667,1,0],[81000,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[81348,1,0],[81667,1,0],[82000,1,0]]},{"lengthInSteps":16,"bpm":180,"changeBPM":false,"mustHitSection":true,"sectionNotes":[[82666.66666666667,1,0],[82999.66666666667,0,0],[83166.66666666667,3,0],[83333.66666666667,1,0],[83667,1,0]],"typeOfSection":0},{"lengthInSteps":16,"bpm":180,"changeBPM":false,"mustHitSection":true,"sectionNotes":[[84014.66666666667,1,0],[84333.66666666667,1,0],[84666.66666666667,1,0]],"typeOfSection":0},{"lengthInSteps":16,"bpm":180,"changeBPM":false,"mustHitSection":true,"sectionNotes":[],"typeOfSection":0}],"needsVoices":true,"speed":1.5,"player1":"bf","player2":"dad"},"bpm":180,"sections":65,"notes":[{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[10667,2,0],[11000,0,0],[11333,2,0],[11750,0,0],[11833,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[12000,2,0],[12333,0,0],[12667,2,0],[13083,0,0],[13250,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[13333.666666666666,2,0],[13666.666666666666,0,0],[13999.666666666666,2,0],[14416.666666666666,0,0],[14499.666666666666,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[14666.666666666666,2,0],[14833.666666666666,3,0],[14999.666666666666,0,0],[15333.666666666666,2,0],[15749.666666666666,0,0],[15916.666666666666,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[16000,1,0],[16333,0,0],[16500,3,0],[16667,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[17348,1,0],[17750,0,0],[17917,0,0],[18083,3,0],[18250,3,0],[18417,3,0],[18583,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[18666.666666666668,1,0],[18999.666666666668,0,0],[19166.666666666668,3,0],[19333.666666666668,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[20014.666666666668,1,0],[20416.666666666668,0,0],[20583.666666666668,0,0],[20749.666666666668,3,0],[20916.666666666668,3,0],[21083.666666666668,3,0],[21249.666666666668,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[21750,2,0],[22083,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[22833,1,0],[23000,3,0],[23250,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[24417,2,0],[24750,1,0],[25000,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[25342,2,0],[25583,0,0],[25917,3,0],[26083,2,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[27083.333333333332,2,0],[27416.333333333332,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[28166.333333333332,1,0],[28333.333333333332,3,0],[28583.333333333332,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[29750.333333333332,2,0],[30083.333333333332,1,0],[30333.333333333332,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[30675.333333333332,2,0],[30916.333333333332,0,0],[31250.333333333332,3,0],[31416.333333333332,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[32167,0,0],[32333,3,0],[32500,2,0],[33000,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[33500,2,0],[33667,3,0],[34083,2,0],[34417,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[34669,0,0],[35000,1,0],[35333,3,0],[35667,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[36008,2,0],[36333,3,0],[36750,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[37583,1,0],[38083,0,0],[38333,1,0],[37750,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[38679,0,0],[39167,0,0],[39333,2,0],[39500,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[40167,0,0],[40333,3,0],[40750,2,0],[40917,3,0],[41250,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[41337,4,0],[41750,6,0],[42083,6,0],[42417,4,0],[42583,5,0],[41348,0,0],[41750,0,0],[42167,2,0],[42333,3,0],[41583,1,0],[41917,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[42833.666666666664,0,0],[42999.666666666664,3,0],[43166.666666666664,2,0],[43666.666666666664,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[44166.666666666664,2,0],[44333.666666666664,3,0],[44749.666666666664,2,0],[45083.666666666664,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[45335.666666666664,0,0],[45666.666666666664,1,0],[45999.666666666664,3,0],[46333.666666666664,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[46674.666666666664,2,0],[46999.666666666664,3,0],[47416.666666666664,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[48249.666666666664,1,0],[48749.666666666664,0,0],[48999.666666666664,1,0],[48416.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[49345.666666666664,0,0],[49833.666666666664,0,0],[49999.666666666664,2,0],[50166.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[50833.666666666664,0,0],[50999.666666666664,3,0],[51416.666666666664,2,0],[51583.666666666664,3,0],[51916.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[52014.666666666664,0,0],[52417,2,0],[52750,3,0],[53000,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[53333.666666666664,2,0],[53666.666666666664,0,0],[53999.666666666664,2,0],[54416.666666666664,0,0],[54499.666666666664,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[54666.666666666664,2,0],[54999.666666666664,0,0],[55333.666666666664,2,0],[55749.666666666664,0,0],[55916.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[56000.33333333333,2,0],[56333.33333333333,0,0],[56666.33333333333,2,0],[57083.33333333333,0,0],[57166.33333333333,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[57333.33333333333,2,0],[57500.33333333333,3,0],[57666.33333333333,0,0],[58000.33333333333,2,0],[58416.33333333333,0,0],[58583.33333333333,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[58666.666666666664,1,0],[58999.666666666664,0,0],[59166.666666666664,3,0],[59333.666666666664,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[60014.666666666664,1,0],[60416.666666666664,0,0],[60583.666666666664,0,0],[60749.666666666664,3,0],[60916.666666666664,3,0],[61083.666666666664,3,0],[61249.666666666664,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[61333.33333333333,1,0],[61666.33333333333,0,0],[61833.33333333333,3,0],[62000.33333333333,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[62681.33333333333,1,0],[63083.33333333333,0,0],[63250.33333333333,0,0],[63416.33333333333,3,0],[63583.33333333333,3,0],[63750.33333333333,3,0],[63916.33333333333,3,0],[62667,4,0],[63000,6,0],[63333,6,0],[63667,4,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[64416.666666666664,2,0],[64583.666666666664,1,0],[64749.666666666664,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[65499.666666666664,1,0],[65666.66666666666,3,0],[65916.66666666666,0,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[67083.66666666666,2,0],[67416.66666666666,1,0],[67666.66666666666,0,0],[67833.66666666666,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[68008.66666666666,2,0],[68166.66666666666,3,0],[68249.66666666666,0,0],[68416.66666666666,1,0],[68583.66666666666,3,0],[68749.66666666666,2,0],[68000,4,0],[68167,5,0],[68500,7,0],[68833,5,0],[69000,4,0],[69167,5,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[69750,2,0],[69917,1,0],[70083,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[70833,1,0],[71000,3,0],[71250,0,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[72417,2,0],[72750,1,0],[73000,0,0],[73167,1,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[73342,2,0],[73583,0,0],[73917,3,0],[74083,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[74667,2,0],[75000,0,0],[75167,1,0],[75750,0,0],[75833,3,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[76000,2,0],[76333,0,0],[76667,2,0],[77000,2,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[77333.66666666667,2,0],[77666.66666666667,0,0],[77833.66666666667,1,0],[78416.66666666667,0,0],[78499.66666666667,3,0]]},{"mustHitSection":true,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[78666.66666666667,2,0],[78999.66666666667,0,0],[79333.66666666667,2,0],[79666.66666666667,2,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[80000,1,0],[80333,0,0],[80500,3,0],[80667,1,0],[81000,1,0]]},{"mustHitSection":false,"typeOfSection":0,"lengthInSteps":16,"sectionNotes":[[81348,1,0],[81667,1,0],[82000,1,0]]},{"lengthInSteps":16,"bpm":180,"changeBPM":false,"mustHitSection":true,"sectionNotes":[[82666.66666666667,1,0],[82999.66666666667,0,0],[83166.66666666667,3,0],[83333.66666666667,1,0],[83667,1,0]],"typeOfSection":0},{"lengthInSteps":16,"bpm":180,"changeBPM":false,"mustHitSection":true,"sectionNotes":[[84014.66666666667,1,0],[84333.66666666667,1,0],[84666.66666666667,1,0]],"typeOfSection":0},{"lengthInSteps":16,"bpm":180,"changeBPM":false,"mustHitSection":true,"sectionNotes":[],"typeOfSection":0}]}
\ No newline at end of file
diff --git a/assets/images/menuBG.png-autosave.kra b/assets/images/menuBG.png-autosave.kra
new file mode 100644
index 0000000..7fcceeb
Binary files /dev/null and b/assets/images/menuBG.png-autosave.kra differ
diff --git a/assets/images/menuBG.png~ b/assets/images/menuBG.png~
new file mode 100644
index 0000000..6586348
Binary files /dev/null and b/assets/images/menuBG.png~ differ
diff --git a/assets/images/menuDesat.png b/assets/images/menuDesat.png
new file mode 100644
index 0000000..5d3feae
Binary files /dev/null and b/assets/images/menuDesat.png differ
diff --git a/assets/images/menuDesat.png~ b/assets/images/menuDesat.png~
new file mode 100644
index 0000000..09acbbb
Binary files /dev/null and b/assets/images/menuDesat.png~ differ
diff --git a/source/ChartingState.hx b/source/ChartingState.hx
index 070d555..deeb349 100644
--- a/source/ChartingState.hx
+++ b/source/ChartingState.hx
@@ -28,7 +28,9 @@ import openfl.events.Event;
import openfl.events.IOErrorEvent;
import openfl.events.IOErrorEvent;
import openfl.events.IOErrorEvent;
+import openfl.media.Sound;
import openfl.net.FileReference;
+import openfl.utils.ByteArray;
using StringTools;
@@ -762,6 +764,13 @@ class ChartingState extends MusicBeatState
FlxG.resetState();
}
+ var mp3File:Sound;
+ var waveForm:FlxSprite;
+
+ function drawWave():Void
+ {
+ }
+
private function saveLevel()
{
var json = {
diff --git a/source/FreeplayState.hx b/source/FreeplayState.hx
index 1937447..f906e8f 100644
--- a/source/FreeplayState.hx
+++ b/source/FreeplayState.hx
@@ -1,10 +1,15 @@
package;
+import flash.text.TextField;
import flixel.FlxG;
import flixel.FlxSprite;
import flixel.addons.display.FlxGridOverlay;
import flixel.group.FlxGroup.FlxTypedGroup;
+import flixel.math.FlxMath;
import flixel.text.FlxText;
+import flixel.util.FlxColor;
+import htmlparser.HtmlDocument;
+import lime.utils.Assets;
class FreeplayState extends MusicBeatState
{
@@ -13,12 +18,19 @@ class FreeplayState extends MusicBeatState
var selector:FlxText;
var curSelected:Int = 0;
+ var scoreText:FlxText;
+ var lerpScore:Int = 0;
+ var intendedScore:Int = 0;
+
private var grpSongs:FlxTypedGroup;
override function create()
{
- if (!FlxG.sound.music.playing)
- FlxG.sound.playMusic('assets/music/freakyMenu' + TitleState.soundExt);
+ if (FlxG.sound.music != null)
+ {
+ if (!FlxG.sound.music.playing)
+ FlxG.sound.playMusic('assets/music/freakyMenu' + TitleState.soundExt);
+ }
var isDebug:Bool = false;
@@ -53,6 +65,17 @@ class FreeplayState extends MusicBeatState
// songText.screenCenter(X);
}
+ scoreText = new FlxText(FlxG.width * 0.7, 5, 0, "", 32);
+ // scoreText.autoSize = false;
+ scoreText.setFormat("assets/fonts/vcr.ttf", 32, FlxColor.WHITE, RIGHT);
+ // scoreText.alignment = RIGHT;
+
+ var scoreBG:FlxSprite = new FlxSprite(scoreText.x - 6, 0).makeGraphic(Std.int(FlxG.width * 0.35), 40, 0xFF000000);
+ scoreBG.alpha = 0.6;
+ add(scoreBG);
+
+ add(scoreText);
+
changeSelection();
// FlxG.sound.playMusic('assets/music/title' + TitleState.soundExt, 0);
@@ -65,12 +88,33 @@ class FreeplayState extends MusicBeatState
var swag:Alphabet = new Alphabet(1, 0, "swag");
+ // JUST DOIN THIS SHIT FOR TESTING!!!
+ /*
+ var md:String = Markdown.markdownToHtml(Assets.getText('CHANGELOG.md'));
+
+ var texFel:TextField = new TextField();
+ texFel.width = FlxG.width;
+ texFel.height = FlxG.height;
+ // texFel.
+ texFel.htmlText = md;
+
+ FlxG.stage.addChild(texFel);
+
+ // scoreText.textField.htmlText = md;
+
+ trace(md);
+ */
+
super.create();
}
override function update(elapsed:Float)
{
super.update(elapsed);
+
+ lerpScore = Math.floor(FlxMath.lerp(lerpScore, intendedScore, 0.4));
+ scoreText.text = "PERSONAL BEST:" + lerpScore;
+
var upP = controls.UP_P;
var downP = controls.DOWN_P;
var accepted = controls.ACCEPT;
@@ -94,12 +138,15 @@ class FreeplayState extends MusicBeatState
PlayState.SONG = Song.loadFromJson(songs[curSelected].toLowerCase(), songs[curSelected].toLowerCase());
PlayState.isStoryMode = false;
FlxG.switchState(new PlayState());
- FlxG.sound.music.stop();
+ if (FlxG.sound.music != null)
+ FlxG.sound.music.stop();
}
}
function changeSelection(change:Int = 0)
{
+ NGio.logEvent('Fresh');
+
curSelected += change;
if (curSelected < 0)
@@ -109,6 +156,9 @@ class FreeplayState extends MusicBeatState
// selector.y = (70 * curSelected) + 30;
+ intendedScore = Highscore.getScore(songs[curSelected], 1);
+ // lerpScore = 0;
+
var bullShit:Int = 0;
for (item in grpSongs.members)
diff --git a/source/Highscore.hx b/source/Highscore.hx
new file mode 100644
index 0000000..f587a3a
--- /dev/null
+++ b/source/Highscore.hx
@@ -0,0 +1,62 @@
+package;
+
+import flixel.FlxG;
+
+class Highscore
+{
+ public static var songScores:Map = new Map();
+
+ public static function saveScore(song:String, score:Int = 0, ?diff:Int = 0):Void
+ {
+ var daSong:String = formatSong(song, diff);
+
+ NGio.postScore(score, song);
+
+ if (songScores.exists(daSong))
+ {
+ if (songScores.get(daSong) < score)
+ setScore(daSong, score);
+ }
+ else
+ setScore(daSong, score);
+ }
+
+ /**
+ * YOU SHOULD FORMAT SONG WITH formatSong() BEFORE TOSSING IN SONG VARIABLE
+ */
+ static function setScore(song:String, score:Int):Void
+ {
+ // Reminder that I don't need to format this song, it should come formatted!
+ songScores.set(song, score);
+ FlxG.save.data.songScores = songScores;
+ FlxG.save.flush();
+ }
+
+ public static function formatSong(song:String, diff:Int):String
+ {
+ var daSong:String = song;
+
+ if (diff == 0)
+ daSong += '-easy';
+ else if (diff == 2)
+ daSong += '-hard';
+
+ return daSong;
+ }
+
+ public static function getScore(song:String, diff:Int):Int
+ {
+ if (!songScores.exists(formatSong(song, diff)))
+ setScore(formatSong(song, diff), 0);
+
+ return songScores.get(formatSong(song, diff));
+ }
+
+ public static function load():Void
+ {
+ if (FlxG.save.data.songScores != null)
+ {
+ songScores = FlxG.save.data.songScores;
+ }
+ }
+}
diff --git a/source/MainMenuState.hx b/source/MainMenuState.hx
index 19ddb46..cdabcbb 100644
--- a/source/MainMenuState.hx
+++ b/source/MainMenuState.hx
@@ -6,8 +6,11 @@ import flixel.FlxSprite;
import flixel.effects.FlxFlicker;
import flixel.graphics.frames.FlxAtlasFrames;
import flixel.group.FlxGroup.FlxTypedGroup;
+import flixel.text.FlxText;
import flixel.tweens.FlxEase;
import flixel.tweens.FlxTween;
+import flixel.util.FlxColor;
+import lime.app.Application;
class MainMenuState extends MusicBeatState
{
@@ -15,7 +18,7 @@ class MainMenuState extends MusicBeatState
var menuItems:FlxTypedGroup;
- var optionShit:Array = ['story mode', 'freeplay', 'donate'];
+ var optionShit:Array = ['story mode', 'freeplay', 'options', 'donate'];
var magenta:FlxSprite;
var camFollow:FlxObject;
@@ -36,7 +39,7 @@ class MainMenuState extends MusicBeatState
camFollow = new FlxObject(0, 0, 1, 1);
add(camFollow);
- magenta = new FlxSprite(-80).loadGraphic(AssetPaths.menuBGMagenta__png);
+ magenta = new FlxSprite(-80).loadGraphic(AssetPaths.menuDesat__png);
magenta.scrollFactor.x = 0;
magenta.scrollFactor.y = 0.18;
magenta.setGraphicSize(Std.int(magenta.width * 1.1));
@@ -44,6 +47,7 @@ class MainMenuState extends MusicBeatState
magenta.screenCenter();
magenta.visible = false;
magenta.antialiasing = true;
+ magenta.color = 0xFFfd719b;
add(magenta);
// magenta.scrollFactor.set();
@@ -68,6 +72,11 @@ class MainMenuState extends MusicBeatState
FlxG.camera.follow(camFollow, null, 0.06);
+ var versionShit:FlxText = new FlxText(5, FlxG.height - 18, 0, "v" + Application.current.meta.get('version'));
+ versionShit.scrollFactor.set();
+ versionShit.setFormat("VCR OSD Mono", 16, FlxColor.WHITE, LEFT, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK);
+ add(versionShit);
+
changeItem();
super.create();
@@ -133,6 +142,8 @@ class MainMenuState extends MusicBeatState
FlxG.switchState(new StoryMenuState());
case 'freeplay':
FlxG.switchState(new FreeplayState());
+ case 'options':
+ FlxG.switchState(new OptionsMenu());
}
});
}
diff --git a/source/MusicBeatSubstate.hx b/source/MusicBeatSubstate.hx
index 0e452e9..511f597 100644
--- a/source/MusicBeatSubstate.hx
+++ b/source/MusicBeatSubstate.hx
@@ -1,5 +1,6 @@
package;
+import flixel.FlxG;
import flixel.FlxSubState;
class MusicBeatSubstate extends FlxSubState
diff --git a/source/NGio.hx b/source/NGio.hx
index f90bca4..2073c07 100644
--- a/source/NGio.hx
+++ b/source/NGio.hx
@@ -146,6 +146,15 @@ class NGio
// NGio.scoreboardArray = NG.core.scoreBoards.get(8004).scores;
}
+ inline static public function logEvent(event:String)
+ {
+ if (isLoggedIn)
+ {
+ NG.core.calls.event.logEvent(event);
+ trace('should have logged: ' + event);
+ }
+ }
+
inline static public function unlockMedal(id:Int)
{
if (isLoggedIn)
diff --git a/source/OptionsMenu.hx b/source/OptionsMenu.hx
new file mode 100644
index 0000000..c79c3ec
--- /dev/null
+++ b/source/OptionsMenu.hx
@@ -0,0 +1,29 @@
+package;
+
+import flixel.FlxG;
+import flixel.FlxSprite;
+import flixel.util.FlxColor;
+
+class OptionsMenu extends MusicBeatState
+{
+ override function create()
+ {
+ var menuBG:FlxSprite = new FlxSprite().loadGraphic(AssetPaths.menuDesat__png);
+ menuBG.color = 0xFFea71fd;
+ menuBG.setGraphicSize(Std.int(menuBG.width * 1.1));
+ menuBG.updateHitbox();
+ menuBG.screenCenter();
+ menuBG.antialiasing = true;
+ add(menuBG);
+
+ super.create();
+ }
+
+ override function update(elapsed:Float)
+ {
+ if (controls.BACK)
+ FlxG.switchState(new MainMenuState());
+
+ super.update(elapsed);
+ }
+}
diff --git a/source/OptionsSubState.hx b/source/OptionsSubState.hx
new file mode 100644
index 0000000..1995b86
--- /dev/null
+++ b/source/OptionsSubState.hx
@@ -0,0 +1,11 @@
+package;
+
+class OptionsSubState extends MusicBeatSubstate
+{
+ var textMenuItems:Array = ['Master Volume', 'Sound Volume'];
+
+ public function new()
+ {
+ super();
+ }
+}
diff --git a/source/PlayState.hx b/source/PlayState.hx
index 0163efc..9ca8723 100644
--- a/source/PlayState.hx
+++ b/source/PlayState.hx
@@ -562,7 +562,7 @@ class PlayState extends MusicBeatState
{
if (FlxG.sound.music != null)
{
- vocals.time = FlxG.sound.music.time;
+ vocals.time = Conductor.songPosition;
FlxG.sound.music.play();
vocals.play();
@@ -595,9 +595,9 @@ class PlayState extends MusicBeatState
openSubState(new PauseSubState(boyfriend.getScreenPosition().x, boyfriend.getScreenPosition().y));
}
- if (FlxG.keys.justPressed.ESCAPE)
+ if (FlxG.keys.justPressed.SEVEN)
{
- // FlxG.switchState(new ChartingState());
+ FlxG.switchState(new ChartingState());
}
// FlxG.watch.addQuick('VOL', vocals.amplitudeLeft);
@@ -792,6 +792,7 @@ class PlayState extends MusicBeatState
}
daNote.y = (strumLine.y - (Conductor.songPosition - daNote.strumTime) * (0.45 * PlayState.SONG.speed));
+
// WIP interpolation shit? Need to fix the pause issue
// daNote.y = (strumLine.y - (songTime - daNote.strumTime) * (0.45 * PlayState.SONG.speed));
@@ -820,11 +821,7 @@ class PlayState extends MusicBeatState
{
trace('SONG DONE' + isStoryMode);
-
- #if !switch
- NGio.postScore(songScore, SONG.song);
- #end
-
+ Highscore.saveScore(SONG.song, songScore, storyDifficulty);
if (isStoryMode)
{
@@ -838,10 +835,7 @@ class PlayState extends MusicBeatState
StoryMenuState.weekUnlocked[1] = true;
- #if !switch
NGio.unlockMedal(60961);
- #end
-
FlxG.save.data.weekUnlocked = StoryMenuState.weekUnlocked;
FlxG.save.flush();
diff --git a/source/StoryMenuState.hx b/source/StoryMenuState.hx
index d88ab48..ca6ba28 100644
--- a/source/StoryMenuState.hx
+++ b/source/StoryMenuState.hx
@@ -38,8 +38,11 @@ class StoryMenuState extends MusicBeatState
override function create()
{
- if (!FlxG.sound.music.playing)
- FlxG.sound.playMusic('assets/music/freakyMenu' + TitleState.soundExt);
+ if (FlxG.sound.music != null)
+ {
+ if (!FlxG.sound.music.playing)
+ FlxG.sound.playMusic('assets/music/freakyMenu' + TitleState.soundExt);
+ }
persistentUpdate = persistentDraw = true;
@@ -300,6 +303,10 @@ class StoryMenuState extends MusicBeatState
for (item in grpWeekText.members)
{
item.targetY = bullShit - curWeek;
+ if (item.targetY == Std.int(0))
+ item.alpha = 1;
+ else
+ item.alpha = 0.6;
bullShit++;
}
diff --git a/source/TitleState.hx b/source/TitleState.hx
index 172e8fe..0035635 100644
--- a/source/TitleState.hx
+++ b/source/TitleState.hx
@@ -36,13 +36,13 @@ class TitleState extends MusicBeatState
['Ritz dx', 'rest in peace'], ['rate five', 'pls no blam'], ['rhythm gaming', 'ultimate'], ['game of the year', 'forever'],
['you already know', 'we really out here'], ['rise and grind', 'love to luis'], ['like parappa', 'but cooler'],
['album of the year', 'chuckie finster'], ["free gitaroo man", "with love to wandaboy"], ['better than geometry dash', 'fight me robtop'],
- ['kiddbrute for president', 'vote now']];
+ ['kiddbrute for president', 'vote now'], ['play dead estate', 'on newgrounds'], ['this is a god damn prototype', 'we workin on it okay'],
+ ['WOMEN ARE real', 'this is official']];
var curWacky:Array = [];
var wackyImage:FlxSprite;
-
override public function create():Void
{
#if (!web)
@@ -57,16 +57,21 @@ class TitleState extends MusicBeatState
super.create();
-
#if (!switch && !debug && NG_LOGIN)
-
var ng:NGio = new NGio(APIStuff.API, APIStuff.EncKey);
#end
+ FlxG.save.bind('funkin', 'ninjamuffin99');
+
+ Highscore.load();
+
+ if (FlxG.save.data.weekUnlocked != null)
+ {
+ StoryMenuState.weekUnlocked = FlxG.save.data.weekUnlocked;
+ }
+
#if SKIP_TO_PLAYSTATE
-
- FlxG.switchState(new StoryMenuState());
-
+ FlxG.switchState(new FreeplayState());
#else
startIntro();
#end
@@ -99,13 +104,6 @@ class TitleState extends MusicBeatState
FlxG.sound.playMusic('assets/music/freakyMenu' + TitleState.soundExt, 0);
FlxG.sound.music.fadeIn(4, 0, 0.7);
-
- FlxG.save.bind('funkin', 'ninjamuffin99');
-
- if (FlxG.save.data.weekUnlocked != null)
- {
- StoryMenuState.weekUnlocked = FlxG.save.data.weekUnlocked;
- }
}
Conductor.changeBPM(102);
@@ -191,6 +189,12 @@ class TitleState extends MusicBeatState
override function update(elapsed:Float)
{
Conductor.songPosition = FlxG.sound.music.time;
+ // FlxG.watch.addQuick('amp', FlxG.sound.music.amplitude);
+
+ if (FlxG.keys.justPressed.F)
+ {
+ FlxG.fullscreen = !FlxG.fullscreen;
+ }
var pressedEnter:Bool = FlxG.keys.justPressed.ENTER;
@@ -204,9 +208,12 @@ class TitleState extends MusicBeatState
if (pressedEnter && !transitioning && skippedIntro)
{
-
#if !switch
NGio.unlockMedal(60960);
+
+ // If it's Friday according to da clock
+ if (Date.now().getDay() == 5)
+ NGio.unlockMedal(61034);
#end
titleText.animation.play('press');
diff --git a/source/io/newgrounds/Call.hx b/source/io/newgrounds/Call.hx
deleted file mode 100644
index bd5d7ac..0000000
--- a/source/io/newgrounds/Call.hx
+++ /dev/null
@@ -1,227 +0,0 @@
-package io.newgrounds;
-
-import io.newgrounds.utils.Dispatcher;
-import io.newgrounds.utils.AsyncHttp;
-import io.newgrounds.objects.Error;
-import io.newgrounds.objects.events.Result;
-import io.newgrounds.objects.events.Result.ResultBase;
-import io.newgrounds.objects.events.Response;
-
-import haxe.ds.StringMap;
-import haxe.Json;
-
-/** A generic way to handle calls agnostic to their type */
-interface ICallable {
-
- public var component(default, null):String;
-
- public function send():Void;
- public function queue():Void;
- public function destroy():Void;
-}
-
-class Call
- implements ICallable {
-
- public var component(default, null):String;
-
- var _core:NGLite;
- var _properties:StringMap;
- var _parameters:StringMap;
- var _requireSession:Bool;
- var _isSecure:Bool;
-
- // --- BASICALLY SIGNALS
- var _dataHandlers:TypedDispatcher>;
- var _successHandlers:Dispatcher;
- var _httpErrorHandlers:TypedDispatcher;
- var _statusHandlers:TypedDispatcher;
-
- public function new (core:NGLite, component:String, requireSession:Bool = false, isSecure:Bool = false) {
-
- _core = core;
- this.component = component;
- _requireSession = requireSession;
- _isSecure = isSecure && core.encryptionHandler != null;
- }
-
- /** adds a property to the input's object. **/
- public function addProperty(name:String, value:Dynamic):Call {
-
- if (_properties == null)
- _properties = new StringMap();
-
- _properties.set(name, value);
-
- return this;
- }
-
- /** adds a parameter to the call's component object. **/
- public function addComponentParameter(name:String, value:Dynamic, defaultValue:Dynamic = null):Call {
-
- if (value == defaultValue)//TODO?: allow sending null value
- return this;
-
- if (_parameters == null)
- _parameters = new StringMap();
-
- _parameters.set(name, value);
-
- return this;
- }
-
- /** Handy callback setter for chained call modifiers. Called when ng.io replies successfully */
- public function addDataHandler(handler:Response->Void):Call {
-
- if (_dataHandlers == null)
- _dataHandlers = new TypedDispatcher>();
-
- _dataHandlers.add(handler);
- return this;
- }
-
- /** Handy callback setter for chained call modifiers. Called when ng.io replies successfully */
- public function addSuccessHandler(handler:Void->Void):Call {
-
- if (_successHandlers == null)
- _successHandlers = new Dispatcher();
-
- _successHandlers.add(handler);
- return this;
- }
-
- /** Handy callback setter for chained call modifiers. Called when ng.io does not reply for any reason */
- public function addErrorHandler(handler:Error->Void):Call {
-
- if (_httpErrorHandlers == null)
- _httpErrorHandlers = new TypedDispatcher();
-
- _httpErrorHandlers.add(handler);
- return this;
- }
-
- /** Handy callback setter for chained call modifiers. No idea when this is called; */
- public function addStatusHandler(handler:Int->Void):Call {//TODO:learn what this is for
-
- if (_statusHandlers == null)
- _statusHandlers = new TypedDispatcher();
-
- _statusHandlers.add(handler);
- return this;
- }
-
- /**
- * Sends the call to the server, do not modify this object after calling this
- * @param secure If encryption is enabled, it will encrypt the call.
- **/
- public function send():Void {
-
- var data:Dynamic = {};
- data.app_id = _core.appId;
- data.call = {};
- data.call.component = component;
-
- if (_core.debug)
- addProperty("debug", true);
-
- if (_properties == null || !_properties.exists("session_id")) {
- // --- HAS NO SESSION ID
-
- if (_core.sessionId != null) {
- // --- AUTO ADD SESSION ID
-
- addProperty("session_id", _core.sessionId);
-
- } else if (_requireSession){
-
- _core.logError(new Error('cannot send "$component" call without a sessionId'));
- return;
- }
- }
-
- if (_properties != null) {
-
- for (field in _properties.keys())
- Reflect.setField(data, field, _properties.get(field));
- }
-
- if (_parameters != null) {
-
- data.call.parameters = {};
-
- for (field in _parameters.keys())
- Reflect.setField(data.call.parameters, field, _parameters.get(field));
- }
-
- _core.logVerbose('Post - ${Json.stringify(data)}');
-
- if (_isSecure) {
-
- var secureData = _core.encryptionHandler(Json.stringify(data.call));
- data.call = {};
- data.call.secure = secureData;
-
- _core.logVerbose(' secure - $secureData');
- }
-
- _core.markCallPending(this);
-
- AsyncHttp.send(_core, Json.stringify(data), onData, onHttpError, onStatus);
- }
-
- /** Adds the call to the queue */
- public function queue():Void {
-
- _core.queueCall(this);
- }
-
- function onData(reply:String):Void {
-
- _core.logVerbose('Reply - $reply');
-
- if (_dataHandlers == null && _successHandlers == null)
- return;
-
- var response = new Response(_core, reply);
-
- if (_dataHandlers != null)
- _dataHandlers.dispatch(response);
-
- if (response.success && response.result.success && _successHandlers != null)
- _successHandlers.dispatch();
-
- destroy();
- }
-
- function onHttpError(message:String):Void {
-
- _core.logError(message);
-
- if (_httpErrorHandlers == null)
- return;
-
- var error = new Error(message);
- _httpErrorHandlers.dispatch(error);
- }
-
- function onStatus(status:Int):Void {
-
- if (_statusHandlers == null)
- return;
-
- _statusHandlers.dispatch(status);
- }
-
- public function destroy():Void {
-
- _core = null;
-
- _properties = null;
- _parameters = null;
-
- _dataHandlers = null;
- _successHandlers = null;
- _httpErrorHandlers = null;
- _statusHandlers = null;
- }
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/NG.hx b/source/io/newgrounds/NG.hx
deleted file mode 100644
index 3445443..0000000
--- a/source/io/newgrounds/NG.hx
+++ /dev/null
@@ -1,475 +0,0 @@
-package io.newgrounds;
-
-#if ng_lite
-typedef NG = NGLite; //TODO: test and make lite UI
-#else
-import io.newgrounds.utils.Dispatcher;
-import io.newgrounds.objects.Error;
-import io.newgrounds.objects.events.Result.SessionResult;
-import io.newgrounds.objects.events.Result.MedalListResult;
-import io.newgrounds.objects.events.Result.ScoreBoardResult;
-import io.newgrounds.objects.events.Response;
-import io.newgrounds.objects.User;
-import io.newgrounds.objects.Medal;
-import io.newgrounds.objects.Session;
-import io.newgrounds.objects.ScoreBoard;
-
-import haxe.ds.IntMap;
-import haxe.Timer;
-
-/**
- * The Newgrounds API for Haxe.
- * Contains many things ripped from MSGhero
- * - https://github.com/MSGhero/NG.hx
- * @author GeoKureli
- */
-class NG extends NGLite {
-
- static public var core(default, null):NG;
- static public var onCoreReady(default, null):Dispatcher = new Dispatcher();
-
- // --- DATA
-
- /** The logged in user */
- public var user(get, never):User;
- function get_user():User {
-
- if (_session == null)
- return null;
-
- return _session.user;
- }
- public var passportUrl(get, never):String;
- function get_passportUrl():String {
-
- if (_session == null || _session.status != SessionStatus.REQUEST_LOGIN)
- return null;
-
- return _session.passportUrl;
- }
- public var medals(default, null):IntMap;
- public var scoreBoards(default, null):IntMap;
-
- // --- EVENTS
-
- public var onLogin(default, null):Dispatcher;
- public var onLogOut(default, null):Dispatcher;
- public var onMedalsLoaded(default, null):Dispatcher;
- public var onScoreBoardsLoaded(default, null):Dispatcher;
-
- // --- MISC
-
- public var loggedIn(default, null):Bool;
- public var attemptingLogin(default, null):Bool;
-
- var _loginCancelled:Bool;
- var _passportCallback:Void->Void;
-
- var _session:Session;
-
- /**
- * Iniitializes the API, call before utilizing any other component
- * @param appId The unique ID of your app as found in the 'API Tools' tab of your Newgrounds.com project.
- * @param sessionId A unique session id used to identify the active user.
- **/
- public function new(appId = "test", sessionId:String = null, ?onSessionFail:Error->Void) {
-
- _session = new Session(this);
- onLogin = new Dispatcher();
- onLogOut = new Dispatcher();
- onMedalsLoaded = new Dispatcher();
- onScoreBoardsLoaded = new Dispatcher();
-
- attemptingLogin = sessionId != null;
-
- super(appId, sessionId, onSessionFail);
- }
-
- /**
- * Creates NG.core, the heart and soul of the API. This is not the only way to create an instance,
- * nor is NG a forced singleton, but it's the only way to set the static NG.core.
- **/
- static public function create(appId = "test", sessionId:String = null, ?onSessionFail:Error->Void):Void {
-
- core = new NG(appId, sessionId, onSessionFail);
-
- onCoreReady.dispatch();
- }
-
- /**
- * Creates NG.core, and tries to create a session. This is not the only way to create an instance,
- * nor is NG a forced singleton, but it's the only way to set the static NG.core.
- **/
- static public function createAndCheckSession
- ( appId = "test"
- , backupSession:String = null
- , ?onSessionFail:Error->Void
- ):Void {
-
- var session = NGLite.getSessionId();
- if (session == null)
- session = backupSession;
-
- create(appId, session, onSessionFail);
-
- core.host = getHost();
- if (core.sessionId != null)
- core.attemptingLogin = true;
- }
-
- // -------------------------------------------------------------------------------------------
- // APP
- // -------------------------------------------------------------------------------------------
-
- override function checkInitialSession(failHandler:Error->Void, response:Response):Void {
-
- onSessionReceive(response, null, null, failHandler);
- }
-
- /**
- * Begins the login process
- *
- * @param onSuccess Called when the login is a success
- * @param onPending Called when the passportUrl has been identified, call NG.core.openPassportLink
- * to open the link continue the process. Leave as null to open the url automatically
- * NOTE: Browser games must open links on click events or else it will be blocked by
- * the popup blocker.
- * @param onFail
- * @param onCancel Called when the user denies the passport connection.
- */
- public function requestLogin
- ( onSuccess:Void->Void = null
- , onPending:Void->Void = null
- , onFail :Error->Void = null
- , onCancel :Void->Void = null
- ):Void {
-
- if (attemptingLogin) {
-
- logError("cannot request another login until the previous attempt is complete");
- return;
- }
-
- if (loggedIn) {
-
- logError("cannot log in, already logged in");
- return;
- }
-
- attemptingLogin = true;
- _loginCancelled = false;
- _passportCallback = null;
-
- var call = calls.app.startSession(true)
- .addDataHandler(onSessionReceive.bind(_, onSuccess, onPending, onFail, onCancel));
-
- if (onFail != null)
- call.addErrorHandler(onFail);
-
- call.send();
- }
-
- function onSessionReceive
- ( response :Response
- , onSuccess:Void->Void = null
- , onPending:Void->Void = null
- , onFail :Error->Void = null
- , onCancel :Void->Void = null
- ):Void {
-
- if (!response.success || !response.result.success) {
-
- sessionId = null;
- endLoginAndCall(null);
-
- if (onFail != null)
- onFail(!response.success ? response.error : response.result.error);
-
- return;
- }
-
- _session.parse(response.result.data.session);
- sessionId = _session.id;
-
- logVerbose('session started - status: ${_session.status}');
-
- if (_session.status == SessionStatus.REQUEST_LOGIN) {
-
- _passportCallback = checkSession.bind(null, onSuccess, onCancel);
- if (onPending != null)
- onPending();
- else
- openPassportUrl();
-
- } else
- checkSession(null, onSuccess, onCancel);
- }
-
- /**
- * Call this once the passport link is established and it will load the passport URL and
- * start checking for session connect periodically
- */
- public function openPassportUrl():Void {
-
- if (passportUrl != null) {
-
- logVerbose('loading passport: ${passportUrl}');
- openPassportHelper(passportUrl);
- onPassportUrlOpen();
-
- } else
- logError("Cannot open passport");
- }
-
-
- static function openPassportHelper(url:String):Void {
- var window = "_blank";
-
- #if flash
- flash.Lib.getURL(new flash.net.URLRequest(url), window);
- #elseif (js && html5)
- js.Browser.window.open(url, window);
- #elseif desktop
-
- #if (sys && windows)
- Sys.command("start", ["", url]);
- #elseif mac
- Sys.command("/usr/bin/open", [url]);
- #elseif linux
- Sys.command("/usr/bin/xdg-open", [path, "&"]);
- #end
-
- #elseif android
- JNI.createStaticMethod
- ( "org/haxe/lime/GameActivity"
- , "openURL"
- , "(Ljava/lang/String;Ljava/lang/String;)V"
- ) (url, window);
- #end
- }
-
- /**
- * Call this once the passport link is established and it will start checking for session connect periodically
- */
- public function onPassportUrlOpen():Void {
-
- if (_passportCallback != null)
- _passportCallback();
-
- _passportCallback = null;
- }
-
- function checkSession(response:Response, onSucceess:Void->Void, onCancel:Void->Void):Void {
-
- if (response != null) {
-
- if (!response.success || !response.result.success) {
-
- log("login cancelled via passport");
-
- endLoginAndCall(onCancel);
- return;
- }
-
- _session.parse(response.result.data.session);
- }
-
- if (_session.status == SessionStatus.USER_LOADED) {
-
- loggedIn = true;
- endLoginAndCall(onSucceess);
- onLogin.dispatch();
-
- } else if (_session.status == SessionStatus.REQUEST_LOGIN){
-
- var call = calls.app.checkSession()
- .addDataHandler(checkSession.bind(_, onSucceess, onCancel));
-
- // Wait 3 seconds and try again
- timer(3.0,
- function():Void {
-
- // Check if cancelLoginRequest was called
- if (!_loginCancelled)
- call.send();
- else {
-
- log("login cancelled via cancelLoginRequest");
- endLoginAndCall(onCancel);
- }
- }
- );
-
- } else
- // The user cancelled the passport
- endLoginAndCall(onCancel);
- }
-
- public function cancelLoginRequest():Void {
-
- if (attemptingLogin)
- _loginCancelled = true;
- }
-
- function endLoginAndCall(callback:Void->Void):Void {
-
- attemptingLogin = false;
- _loginCancelled = false;
-
- if (callback != null)
- callback();
- }
-
- public function logOut(onComplete:Void->Void = null):Void {
-
- var call = calls.app.endSession()
- .addSuccessHandler(onLogOutSuccessful);
-
- if (onComplete != null)
- call.addSuccessHandler(onComplete);
-
- call.addSuccessHandler(onLogOut.dispatch)
- .send();
- }
-
- function onLogOutSuccessful():Void {
-
- _session.expire();
- sessionId = null;
- loggedIn = false;
- }
-
- // -------------------------------------------------------------------------------------------
- // MEDALS
- // -------------------------------------------------------------------------------------------
-
- public function requestMedals(onSuccess:Void->Void = null, onFail:Error->Void = null):Void {
-
- var call = calls.medal.getList()
- .addDataHandler(onMedalsReceived);
-
- if (onSuccess != null)
- call.addSuccessHandler(onSuccess);
-
- if (onFail != null)
- call.addErrorHandler(onFail);
-
- call.send();
- }
-
- function onMedalsReceived(response:Response):Void {
-
- if (!response.success || !response.result.success)
- return;
-
- var idList:Array = new Array();
-
- if (medals == null) {
-
- medals = new IntMap();
-
- for (medalData in response.result.data.medals) {
-
- var medal = new Medal(this, medalData);
- medals.set(medal.id, medal);
- idList.push(medal.id);
- }
- } else {
-
- for (medalData in response.result.data.medals) {
-
- medals.get(medalData.id).parse(medalData);
- idList.push(medalData.id);
- }
- }
-
- logVerbose('${response.result.data.medals.length} Medals received [${idList.join(", ")}]');
-
- onMedalsLoaded.dispatch();
- }
-
- // -------------------------------------------------------------------------------------------
- // SCOREBOARDS
- // -------------------------------------------------------------------------------------------
-
- public function requestScoreBoards(onSuccess:Void->Void = null, onFail:Error->Void = null):Void {
-
- if (scoreBoards != null) {
-
- log("aborting scoreboard request, all scoreboards are loaded");
-
- if (onSuccess != null)
- onSuccess();
-
- return;
- }
-
- var call = calls.scoreBoard.getBoards()
- .addDataHandler(onBoardsReceived);
-
- if (onSuccess != null)
- call.addSuccessHandler(onSuccess);
-
- if (onFail != null)
- call.addErrorHandler(onFail);
-
- call.send();
- }
-
- function onBoardsReceived(response:Response):Void {
-
- if (!response.success || !response.result.success)
- return;
-
- var idList:Array = new Array();
-
- if (scoreBoards == null) {
-
- scoreBoards = new IntMap();
-
- for (boardData in response.result.data.scoreboards) {
-
- var board = new ScoreBoard(this, boardData);
- scoreBoards.set(board.id, board);
- idList.push(board.id);
- }
- }
-
- logVerbose('${response.result.data.scoreboards.length} ScoreBoards received [${idList.join(", ")}]');
-
- onScoreBoardsLoaded.dispatch();
- }
-
- // -------------------------------------------------------------------------------------------
- // HELPERS
- // -------------------------------------------------------------------------------------------
-
- function timer(delay:Float, callback:Void->Void):Void {
-
- var timer = new Timer(Std.int(delay * 1000));
- timer.run = function func():Void {
-
- timer.stop();
- callback();
- }
- }
-
- static var urlParser:EReg = ~/^(?:http[s]?:\/\/)?([^:\/\s]+)(:[0-9]+)?((?:\/\w+)*\/)([\w\-\.]+[^#?\s]+)([^#\s]*)?(#[\w\-]+)?$/i;//TODO:trim
- /** Used to get the current web host of your game. */
- static public function getHost():String {
-
- var url = NGLite.getUrl();
-
- if (url == null || url == "")
- return "";
-
- if (url.indexOf("file") == 0)
- return "";
-
- if (urlParser.match(url))
- return urlParser.matched(1);
-
- return "";
- }
-}
-#end
\ No newline at end of file
diff --git a/source/io/newgrounds/NGLite.hx b/source/io/newgrounds/NGLite.hx
deleted file mode 100644
index 0c9d5bd..0000000
--- a/source/io/newgrounds/NGLite.hx
+++ /dev/null
@@ -1,287 +0,0 @@
-package io.newgrounds;
-
-import haxe.crypto.Base64;
-import haxe.io.Bytes;
-import haxe.PosInfos;
-
-import io.newgrounds.Call.ICallable;
-import io.newgrounds.components.ComponentList;
-import io.newgrounds.crypto.EncryptionFormat;
-import io.newgrounds.crypto.Cipher;
-import io.newgrounds.crypto.Rc4;
-import io.newgrounds.objects.Error;
-import io.newgrounds.objects.events.Response;
-import io.newgrounds.objects.events.Result.ResultBase;
-import io.newgrounds.objects.events.Result.SessionResult;
-import io.newgrounds.utils.Dispatcher;
-
-#if !(html5 || flash || desktop || neko)
- #error "Target not supported, use: Flash, JS/HTML5, cpp or maybe neko";
-#end
-
-/**
- * The barebones NG.io API. Allows API calls with code completion
- * and retrieves server data via strongly typed Objects
- *
- * Contains many things ripped from MSGhero's repo
- * - https://github.com/MSGhero/NG.hx
- *
- * @author GeoKureli
- */
-class NGLite {
-
- static public var core(default, null):NGLite;
- static public var onCoreReady(default, null):Dispatcher = new Dispatcher();
-
- /** Enables verbose logging */
- public var verbose:Bool;
- public var debug:Bool;
- /** The unique ID of your app as found in the 'API Tools' tab of your Newgrounds.com project. */
- public var appId(default, null):String;
- /** The name of the host the game is being played on */
- public var host:String;
-
- @:isVar
- public var sessionId(default, set):String;
- function set_sessionId(value:String):String {
-
- return this.sessionId = value == "" ? null : value;
- }
-
- /** Components used to call the NG server directly */
- public var calls(default, null):ComponentList;
-
- /**
- * Converts an object to an encrypted string that can be decrypted by the server.
- * Set your preffered encrypter here,
- * or just call setDefaultEcryptionHandler with your app's encryption settings
- **/
- public var encryptionHandler:String->String;
-
- /**
- * Iniitializes the API, call before utilizing any other component
- * @param appId The unique ID of your app as found in the 'API Tools' tab of your Newgrounds.com project.
- * @param sessionId A unique session id used to identify the active user.
- **/
- public function new(appId = "test", sessionId:String = null, ?onSessionFail:Error->Void) {
-
- this.appId = appId;
- this.sessionId = sessionId;
-
- calls = new ComponentList(this);
-
- if (this.sessionId != null) {
-
- calls.app.checkSession()
- .addDataHandler(checkInitialSession.bind(onSessionFail))
- .addErrorHandler(initialSessionFail.bind(onSessionFail))
- .send();
- }
- }
-
- function checkInitialSession(onFail:Error->Void, response:Response):Void {
-
- if (!response.success || !response.result.success || response.result.data.session.expired) {
-
- initialSessionFail(onFail, response.success ? response.result.error : response.error);
- }
- }
-
- function initialSessionFail(onFail:Error->Void, error:Error):Void {
-
- sessionId = null;
-
- if (onFail != null)
- onFail(error);
- }
-
- /**
- * Creates NG.core, the heart and soul of the API. This is not the only way to create an instance,
- * nor is NG a forced singleton, but it's the only way to set the static NG.core.
- **/
- static public function create(appId = "test", sessionId:String = null, ?onSessionFail:Error->Void):Void {
-
- core = new NGLite(appId, sessionId, onSessionFail);
-
- onCoreReady.dispatch();
- }
-
- /**
- * Creates NG.core, and tries to create a session. This is not the only way to create an instance,
- * nor is NG a forced singleton, but it's the only way to set the static NG.core.
- **/
- static public function createAndCheckSession
- ( appId = "test"
- , backupSession:String = null
- , ?onSessionFail:Error->Void
- ):Void {
-
- var session = getSessionId();
- if (session == null)
- session = backupSession;
-
- create(appId, session, onSessionFail);
- }
-
- inline static public function getUrl():String {
-
- #if html5
- return js.Browser.document.location.href;
- #elseif flash
- return flash.Lib.current.stage.loaderInfo != null
- ? flash.Lib.current.stage.loaderInfo.url
- : null;
- #else
- return null;
- #end
- }
-
- static public function getSessionId():String {
-
- #if html5
-
- var url = getUrl();
-
- // Check for URL params
- var index = url.indexOf("?");
- if (index != -1) {
-
- // Check for session ID in params
- for (param in url.substr(index + 1).split("&")) {
-
- index = param.indexOf("=");
- if (index != -1 && param.substr(0, index) == "ngio_session_id")
- return param.substr(index + 1);
- }
- }
-
- #elseif flash
-
- if (flash.Lib.current.stage.loaderInfo != null
- && Reflect.hasField(flash.Lib.current.stage.loaderInfo.parameters, "ngio_session_id"))
- return Reflect.field(flash.Lib.current.stage.loaderInfo.parameters, "ngio_session_id");
-
- #end
-
- return null;
-
- // --- EXAMPLE LOADER PARAMS
- //{ "1517703669" : ""
- //, "ng_username" : "GeoKureli"
- //, "NewgroundsAPI_SessionID" : "F1LusbG6P8Qf91w7zeUE37c1752563f366688ac6153996d12eeb111a2f60w2xn"
- //, "NewgroundsAPI_PublisherID" : 1
- //, "NewgroundsAPI_UserID" : 488329
- //, "NewgroundsAPI_SandboxID" : "5a76520e4ae1e"
- //, "ngio_session_id" : "0c6c4e02567a5116734ba1a0cd841dac28a42e79302290"
- //, "NewgroundsAPI_UserName" : "GeoKureli"
- //}
- }
-
- // -------------------------------------------------------------------------------------------
- // CALLS
- // -------------------------------------------------------------------------------------------
-
- var _queuedCalls:Array = new Array();
- var _pendingCalls:Array = new Array();
-
- @:allow(io.newgrounds.Call)
- @:generic
- function queueCall(call:Call):Void {
-
- logVerbose('queued - ${call.component}');
-
- _queuedCalls.push(call);
- checkQueue();
- }
-
- @:allow(io.newgrounds.Call)
- @:generic
- function markCallPending(call:Call):Void {
-
- _pendingCalls.push(call);
-
- call.addDataHandler(function (_):Void { onCallComplete(call); });
- call.addErrorHandler(function (_):Void { onCallComplete(call); });
- }
-
- function onCallComplete(call:ICallable):Void {
-
- _pendingCalls.remove(call);
- checkQueue();
- }
-
- function checkQueue():Void {
-
- if (_pendingCalls.length == 0 && _queuedCalls.length > 0)
- _queuedCalls.shift().send();
- }
-
- // -------------------------------------------------------------------------------------------
- // LOGGING / ERRORS
- // -------------------------------------------------------------------------------------------
-
- /** Called internally, set this to your preferred logging method */
- dynamic public function log(any:Dynamic, ?pos:PosInfos):Void {//TODO: limit access via @:allow
-
- haxe.Log.trace('[Newgrounds API] :: ${any}', pos);
- }
-
- /** used internally, logs if verbose is true */
- inline public function logVerbose(any:Dynamic, ?pos:PosInfos):Void {//TODO: limit access via @:allow
-
- if (verbose)
- log(any, pos);
- }
-
- /** Used internally. Logs by default, set this to your preferred error handling method */
- dynamic public function logError(any:Dynamic, ?pos:PosInfos):Void {//TODO: limit access via @:allow
-
- log('Error: $any', pos);
- }
-
- /** used internally, calls log error if the condition is false. EX: if (assert(data != null, "null data")) */
- inline public function assert(condition:Bool, msg:Dynamic, ?pos:PosInfos):Bool {//TODO: limit access via @:allow
- if (!condition)
- logError(msg, pos);
-
- return condition;
- }
-
- // -------------------------------------------------------------------------------------------
- // ENCRYPTION
- // -------------------------------------------------------------------------------------------
-
- /** Sets */
- public function initEncryption
- ( key :String
- , cipher:Cipher = Cipher.RC4
- , format:EncryptionFormat = EncryptionFormat.BASE_64
- ):Void {
-
- if (cipher == Cipher.NONE)
- encryptionHandler = null;
- else if (cipher == Cipher.RC4)
- encryptionHandler = encryptRc4.bind(key, format);
- else
- throw "aes not yet implemented";
- }
-
- function encryptRc4(key:String, format:EncryptionFormat, data:String):String {
-
- if (format == EncryptionFormat.HEX)
- throw "hex format not yet implemented";
-
- var keyBytes:Bytes;
- if (format == EncryptionFormat.BASE_64)
- keyBytes = Base64.decode(key);
- else
- keyBytes = null;//TODO
-
- var dataBytes = new Rc4(keyBytes).crypt(Bytes.ofString(data));
-
- if (format == EncryptionFormat.BASE_64)
- return Base64.encode(dataBytes);
-
- return null;
- }
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/components/AppComponent.hx b/source/io/newgrounds/components/AppComponent.hx
deleted file mode 100644
index 1ea5b8b..0000000
--- a/source/io/newgrounds/components/AppComponent.hx
+++ /dev/null
@@ -1,44 +0,0 @@
-package io.newgrounds.components;
-
-import io.newgrounds.objects.events.Result;
-import io.newgrounds.objects.events.Result.SessionResult;
-import io.newgrounds.NGLite;
-
-class AppComponent extends Component {
-
- public function new (core:NGLite) { super(core); }
-
- public function startSession(force:Bool = false):Call {
-
- return new Call(_core, "App.startSession")
- .addComponentParameter("force", force, false);
- }
-
- public function checkSession():Call {
-
- return new Call(_core, "App.checkSession", true);
- }
-
- public function endSession():Call {
-
- return new Call(_core, "App.endSession", true);
- }
-
- public function getCurrentVersion(version:String):Call {
-
- return new Call(_core, "App.getCurrentVersion")
- .addComponentParameter("version", version);
- }
-
- public function getHostLicense():Call {
-
- return new Call(_core, "App.getHostLicense")
- .addComponentParameter("host", _core.host);
- }
-
- public function logView():Call {
-
- return new Call(_core, "App.logView")
- .addComponentParameter("host", _core.host);
- }
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/components/Component.hx b/source/io/newgrounds/components/Component.hx
deleted file mode 100644
index 3c588ff..0000000
--- a/source/io/newgrounds/components/Component.hx
+++ /dev/null
@@ -1,13 +0,0 @@
-package io.newgrounds.components;
-
-import io.newgrounds.NGLite;
-
-class Component {
-
- var _core:NGLite;
-
- public function new(core:NGLite) {
-
- this._core = core;
- }
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/components/ComponentList.hx b/source/io/newgrounds/components/ComponentList.hx
deleted file mode 100644
index 315abf4..0000000
--- a/source/io/newgrounds/components/ComponentList.hx
+++ /dev/null
@@ -1,25 +0,0 @@
-package io.newgrounds.components;
-class ComponentList {
-
- var _core:NGLite;
-
- // --- COMPONENTS
- public var medal : MedalComponent;
- public var app : AppComponent;
- public var event : EventComponent;
- public var scoreBoard: ScoreBoardComponent;
- public var loader : LoaderComponent;
- public var gateway : GatewayComponent;
-
- public function new(core:NGLite) {
-
- _core = core;
-
- medal = new MedalComponent (_core);
- app = new AppComponent (_core);
- event = new EventComponent (_core);
- scoreBoard = new ScoreBoardComponent(_core);
- loader = new LoaderComponent (_core);
- gateway = new GatewayComponent (_core);
- }
-}
diff --git a/source/io/newgrounds/components/EventComponent.hx b/source/io/newgrounds/components/EventComponent.hx
deleted file mode 100644
index 2e63177..0000000
--- a/source/io/newgrounds/components/EventComponent.hx
+++ /dev/null
@@ -1,16 +0,0 @@
-package io.newgrounds.components;
-
-import io.newgrounds.objects.events.Result.LogEventResult;
-import io.newgrounds.NGLite;
-
-class EventComponent extends Component {
-
- public function new (core:NGLite){ super(core); }
-
- public function logEvent(eventName:String):Call {
-
- return new Call(_core, "Event.logEvent")
- .addComponentParameter("event_name", eventName)
- .addComponentParameter("host", _core.host);
- }
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/components/GatewayComponent.hx b/source/io/newgrounds/components/GatewayComponent.hx
deleted file mode 100644
index 4f0ece6..0000000
--- a/source/io/newgrounds/components/GatewayComponent.hx
+++ /dev/null
@@ -1,25 +0,0 @@
-package io.newgrounds.components;
-
-import io.newgrounds.objects.events.Result;
-import io.newgrounds.NGLite;
-
-class GatewayComponent extends Component {
-
- public function new (core:NGLite){ super(core); }
-
- public function getDatetime():Call {
-
- return new Call(_core, "Gateway.getDatetime");
- }
-
- public function getVersion():Call {
-
- return new Call(_core, "Gateway.getVersion");
- }
-
- public function ping():Call {
-
- return new Call(_core, "Gateway.ping");
- }
-
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/components/LoaderComponent.hx b/source/io/newgrounds/components/LoaderComponent.hx
deleted file mode 100644
index 717cc2e..0000000
--- a/source/io/newgrounds/components/LoaderComponent.hx
+++ /dev/null
@@ -1,44 +0,0 @@
-package io.newgrounds.components;
-
-import io.newgrounds.objects.events.Result;
-import io.newgrounds.NGLite;
-
-class LoaderComponent extends Component {
-
- public function new (core:NGLite){ super(core); }
-
- public function loadAuthorUrl(redirect:Bool = false):Call {
-
- return new Call(_core, "Loader.loadAuthorUrl")
- .addComponentParameter("host", _core.host)
- .addComponentParameter("redirect", redirect, true);
- }
-
- public function loadMoreGames(redirect:Bool = false):Call {
-
- return new Call(_core, "Loader.loadMoreGames")
- .addComponentParameter("host", _core.host)
- .addComponentParameter("redirect", redirect, true);
- }
-
- public function loadNewgrounds(redirect:Bool = false):Call {
-
- return new Call(_core, "Loader.loadNewgrounds")
- .addComponentParameter("host", _core.host)
- .addComponentParameter("redirect", redirect, true);
- }
-
- public function loadOfficialUrl(redirect:Bool = false):Call {
-
- return new Call(_core, "Loader.loadOfficialUrl")
- .addComponentParameter("host", _core.host)
- .addComponentParameter("redirect", redirect, true);
- }
-
- public function loadReferral(redirect:Bool = false):Call {
-
- return new Call(_core, "Loader.loadReferral")
- .addComponentParameter("host", _core.host)
- .addComponentParameter("redirect", redirect, true);
- }
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/components/MedalComponent.hx b/source/io/newgrounds/components/MedalComponent.hx
deleted file mode 100644
index 7e56621..0000000
--- a/source/io/newgrounds/components/MedalComponent.hx
+++ /dev/null
@@ -1,21 +0,0 @@
-package io.newgrounds.components;
-
-import io.newgrounds.objects.events.Result;
-import io.newgrounds.Call;
-import io.newgrounds.NGLite;
-
-class MedalComponent extends Component {
-
- public function new(core:NGLite):Void { super(core); }
-
- public function unlock(id:Int):Call {
-
- return new Call(_core, "Medal.unlock", true, true)
- .addComponentParameter("id", id);
- }
-
- public function getList():Call {
-
- return new Call(_core, "Medal.getList");
- }
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/components/ScoreBoardComponent.hx b/source/io/newgrounds/components/ScoreBoardComponent.hx
deleted file mode 100644
index 7417e67..0000000
--- a/source/io/newgrounds/components/ScoreBoardComponent.hx
+++ /dev/null
@@ -1,114 +0,0 @@
-package io.newgrounds.components;
-
-import io.newgrounds.objects.User;
-import io.newgrounds.objects.events.Response;
-import io.newgrounds.objects.events.Result;
-import io.newgrounds.objects.events.Result.ScoreBoardResult;
-import io.newgrounds.objects.events.Result.ScoreResult;
-import io.newgrounds.NGLite;
-import io.newgrounds.objects.ScoreBoard;
-
-import haxe.ds.IntMap;
-
-class ScoreBoardComponent extends Component {
-
- public var allById:IntMap;
-
- public function new (core:NGLite){ super(core); }
-
- // -------------------------------------------------------------------------------------------
- // GET SCORES
- // -------------------------------------------------------------------------------------------
-
- public function getBoards():Call {
-
- return new Call(_core, "ScoreBoard.getBoards");
- }
-
- /*function onBoardsReceive(response:Response):Void {
-
- if (!response.result.success)
- return;
-
- allById = new IntMap();
-
- for (boardData in response.result.scoreboards)
- createBoard(boardData);
-
- _core.log('${response.result.scoreboards.length} ScoreBoards loaded');
- }*/
-
- // -------------------------------------------------------------------------------------------
- // GET SCORES
- // -------------------------------------------------------------------------------------------
-
- public function getScores
- ( id :Int
- , limit :Int = 10
- , skip :Int = 0
- , period:Period = Period.DAY
- , social:Bool = false
- , tag :String = null
- , user :Dynamic = null
- ):Call {
-
- if (user != null && !Std.is(user, String) && !Std.is(user, Int))
- user = user.id;
-
- return new Call(_core, "ScoreBoard.getScores")
- .addComponentParameter("id" , id )
- .addComponentParameter("limit" , limit , 10)
- .addComponentParameter("skip" , skip , 0)
- .addComponentParameter("period", period, Period.DAY)
- .addComponentParameter("social", social, false)
- .addComponentParameter("tag" , tag , null)
- .addComponentParameter("user" , user , null);
- }
-
- // -------------------------------------------------------------------------------------------
- // POST SCORE
- // -------------------------------------------------------------------------------------------
-
- public function postScore(id:Int, value:Int, tag:String = null):Call {
-
- return new Call(_core, "ScoreBoard.postScore", true, true)
- .addComponentParameter("id" , id)
- .addComponentParameter("value", value)
- .addComponentParameter("tag" , tag , null);
- }
-
- /*function onScorePosted(response:Response):Void {
-
- if (!response.result.success)
- return;
-
- allById = new IntMap();
-
- //createBoard(data.data.scoreBoard).parseScores(data.data.scores);
- }*/
-
- inline function createBoard(data:Dynamic):ScoreBoard {
-
- var board = new ScoreBoard(_core, data);
- _core.logVerbose('created $board');
-
- allById.set(board.id, board);
-
- return board;
- }
-}
-
-@:enum
-abstract Period(String) to String from String{
-
- /** Indicates scores are from the current day. */
- var DAY = "D";
- /** Indicates scores are from the current week. */
- var WEEK = "W";
- /** Indicates scores are from the current month. */
- var MONTH = "M";
- /** Indicates scores are from the current year. */
- var YEAR = "Y";
- /** Indicates scores are from all-time. */
- var ALL = "A";
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/crypto/Cipher.hx b/source/io/newgrounds/crypto/Cipher.hx
deleted file mode 100644
index 2f4c007..0000000
--- a/source/io/newgrounds/crypto/Cipher.hx
+++ /dev/null
@@ -1,8 +0,0 @@
-package io.newgrounds.crypto;
-
-@:enum
-abstract Cipher(String) to String{
- var NONE = "none";
- var AES_128 = "aes128";
- var RC4 = "rc4";
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/crypto/EncryptionFormat.hx b/source/io/newgrounds/crypto/EncryptionFormat.hx
deleted file mode 100644
index 6e8f17f..0000000
--- a/source/io/newgrounds/crypto/EncryptionFormat.hx
+++ /dev/null
@@ -1,7 +0,0 @@
-package io.newgrounds.crypto;
-
-@:enum
-abstract EncryptionFormat(String) to String {
- var BASE_64 = "base64";
- var HEX = "hex";
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/crypto/Rc4.hx b/source/io/newgrounds/crypto/Rc4.hx
deleted file mode 100644
index 54dafa7..0000000
--- a/source/io/newgrounds/crypto/Rc4.hx
+++ /dev/null
@@ -1,68 +0,0 @@
-package io.newgrounds.crypto;
-
-import haxe.io.Bytes;
-
-/**
- * The following was straight-up ganked from https://github.com/iskolbin/rc4hx
- *
- * You da real MVP iskolbin...
- *
- * The MIT License (MIT)
- *
- * Copyright (c) 2015 iskolbin
- *
- * 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.
-**/
-class Rc4 {
- var perm = Bytes.alloc( 256 );
- var index1: Int = 0;
- var index2: Int = 0;
-
- public function new( key: Bytes ) {
- for ( i in 0...256 ) {
- perm.set( i, i );
- }
-
- var j: Int = 0;
- for ( i in 0...256 ) {
- j = ( j + perm.get( i ) + key.get( i % key.length )) % 256;
- swap( i, j );
- }
- }
-
- inline function swap( i: Int, j: Int ): Void {
- var temp = perm.get( i );
- perm.set( i, perm.get( j ));
- perm.set( j, temp );
- }
-
- public function crypt( input: Bytes ): Bytes {
- var output = Bytes.alloc( input.length );
-
- for ( i in 0...input.length ) {
- index1 = ( index1 + 1 ) % 256;
- index2 = ( index2 + perm.get( index1 )) % 256;
- swap( index1, index2 );
- var j = ( perm.get( index1 ) + perm.get( index2 )) % 256;
- output.set( i, input.get( i ) ^ perm.get( j ));
- }
-
- return output;
- }
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/objects/Error.hx b/source/io/newgrounds/objects/Error.hx
deleted file mode 100644
index 6e82e4e..0000000
--- a/source/io/newgrounds/objects/Error.hx
+++ /dev/null
@@ -1,20 +0,0 @@
-package io.newgrounds.objects;
-class Error {
-
- public var code(default, null):Int;
- public var message(default, null):String;
-
- public function new (message:String, code:Int = 0) {
-
- this.message = message;
- this.code = code;
- }
-
- public function toString():String {
-
- if (code > 0)
- return '#$code - $message';
-
- return message;
- }
-}
diff --git a/source/io/newgrounds/objects/Medal.hx b/source/io/newgrounds/objects/Medal.hx
deleted file mode 100644
index 3cecc7a..0000000
--- a/source/io/newgrounds/objects/Medal.hx
+++ /dev/null
@@ -1,118 +0,0 @@
-package io.newgrounds.objects;
-
-import io.newgrounds.objects.events.Response;
-import io.newgrounds.objects.events.Result.MedalUnlockResult;
-import io.newgrounds.utils.Dispatcher;
-import io.newgrounds.NGLite;
-
-class Medal extends Object {
-
- inline static public var EASY :Int = 1;
- inline static public var MODERATE :Int = 2;
- inline static public var CHALLENGING:Int = 3;
- inline static public var DIFFICULT :Int = 4;
- inline static public var BRUTAL :Int = 5;
-
- static var difficultyNames:Array =
- [ "Easy"
- , "Moderate"
- , "Challenging"
- , "Difficult"
- , "Brutal"
- ];
- // --- FROM SERVER
- public var id (default, null):Int;
- public var name (default, null):String;
- public var description(default, null):String;
- public var icon (default, null):String;
- public var value (default, null):Int;
- public var difficulty (default, null):Int;
- public var secret (default, null):Bool;
- public var unlocked (default, null):Bool;
- // --- HELPERS
- public var difficultyName(get, never):String;
-
- public var onUnlock:Dispatcher;
-
- public function new(core:NGLite, data:Dynamic = null):Void {
-
- onUnlock = new Dispatcher();
-
- super(core, data);
- }
-
- @:allow(io.newgrounds.NG)
- override function parse(data:Dynamic):Void {
-
- var wasLocked = !unlocked;
-
- id = data.id;
- name = data.name;
- description = data.description;
- icon = data.icon;
- value = data.value;
- difficulty = data.difficulty;
- secret = data.secret == 1;
- unlocked = data.unlocked;
-
- super.parse(data);
-
- if (wasLocked && unlocked)
- onUnlock.dispatch();
-
- }
-
- public function sendUnlock():Void {
-
- if (_core.sessionId == null) {
- // --- Unlock regardless, show medal popup to encourage NG signup
- unlocked = true;
- onUnlock.dispatch();
- //TODO: save unlock in local save
- }
-
- _core.calls.medal.unlock(id)
- .addDataHandler(onUnlockResponse)
- .send();
- }
-
- function onUnlockResponse(response:Response):Void {
-
- if (response.success && response.result.success) {
-
- parse(response.result.data.medal);
-
- // --- Unlock response doesn't include unlock=true, so parse won't change it.
- if (!unlocked) {
-
- unlocked = true;
- onUnlock.dispatch();
- }
- }
- }
-
- /** Locks the medal on the client and sends an unlock request, Server responds the same either way. */
- public function sendDebugUnlock():Void {
-
- if (NG.core.sessionId == null) {
-
- onUnlock.dispatch();
-
- } else {
-
- unlocked = false;
-
- sendUnlock();
- }
- }
-
- public function get_difficultyName():String {
-
- return difficultyNames[difficulty - 1];
- }
-
- public function toString():String {
-
- return 'Medal: $id@$name (${unlocked ? "unlocked" : "locked"}, $value pts, $difficultyName).';
- }
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/objects/Object.hx b/source/io/newgrounds/objects/Object.hx
deleted file mode 100644
index 32abd0f..0000000
--- a/source/io/newgrounds/objects/Object.hx
+++ /dev/null
@@ -1,33 +0,0 @@
-package io.newgrounds.objects;
-
-import io.newgrounds.utils.Dispatcher;
-import io.newgrounds.NGLite;
-
-class Object {
-
- var _core:NGLite;
-
- public var onUpdate(default, null):Dispatcher;
-
- public function new(core:NGLite, data:Dynamic = null) {
-
- this._core = core;
-
- onUpdate = new Dispatcher();
-
- if (data != null)
- parse(data);
- }
-
- @:allow(io.newgrounds.NGLite)
- function parse(data:Dynamic):Void {
-
- onUpdate.dispatch();
- }
-
-
- public function destroy():Void {
-
- _core = null;
- }
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/objects/Score.hx b/source/io/newgrounds/objects/Score.hx
deleted file mode 100644
index 0eb6982..0000000
--- a/source/io/newgrounds/objects/Score.hx
+++ /dev/null
@@ -1,17 +0,0 @@
-package io.newgrounds.objects;
-
-/** We don't want to serialize scores since there's a bajillion of them. */
-typedef Score = {
-
- /** The value value in the format selected in your scoreboard settings. */
- var formatted_value:String;
-
- /** The tag attached to this value (if any). */
- var tag:String;
-
- /** The user who earned value. If this property is absent, the value belongs to the active user. */
- var user:User;
-
- /** The integer value of the value. */
- var value:Int;
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/objects/ScoreBoard.hx b/source/io/newgrounds/objects/ScoreBoard.hx
deleted file mode 100644
index 1859b08..0000000
--- a/source/io/newgrounds/objects/ScoreBoard.hx
+++ /dev/null
@@ -1,76 +0,0 @@
-package io.newgrounds.objects;
-
-import io.newgrounds.components.ScoreBoardComponent.Period;
-import io.newgrounds.objects.events.Response;
-import io.newgrounds.objects.events.Result;
-import io.newgrounds.objects.events.Result.ScoreResult;
-import io.newgrounds.NGLite;
-
-class ScoreBoard extends Object {
-
- public var scores(default, null):Array;
-
- /** The numeric ID of the scoreboard.*/
- public var id(default, null):Int;
-
- /** The name of the scoreboard. */
- public var name(default, null):String;
-
- public function new(core:NGLite, data:Dynamic):Void {super(core, data); }
-
- override function parse(data:Dynamic):Void {
-
- id = data.id;
- name = data.name;
-
- super.parse(data);
- }
-
- /**
- * Fetches score data from the server, this removes all of the existing scores cached
- *
- * We don't unify the old and new scores because a user's rank or score may change between requests
- */
- public function requestScores
- ( limit :Int = 10
- , skip :Int = 0
- , period:Period = Period.ALL
- , social:Bool = false
- , tag :String = null
- , user :Dynamic = null
- ):Void {
-
- _core.calls.scoreBoard.getScores(id, limit, skip, period, social, tag, user)
- .addDataHandler(onScoresReceived)
- .send();
- }
-
- function onScoresReceived(response:Response):Void {
-
- if (!response.success || !response.result.success)
- return;
-
- scores = response.result.data.scores;
- _core.logVerbose('received ${scores.length} scores');
-
- onUpdate.dispatch();
- }
-
- public function postScore(value :Int, tag:String = null):Void {
-
- _core.calls.scoreBoard.postScore(id, value, tag)
- .addDataHandler(onScorePosted)
- .send();
- }
-
- function onScorePosted(response:Response):Void {
-
-
- }
-
- public function toString():String {
-
- return 'ScoreBoard: $id@$name';
- }
-
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/objects/Session.hx b/source/io/newgrounds/objects/Session.hx
deleted file mode 100644
index 887df79..0000000
--- a/source/io/newgrounds/objects/Session.hx
+++ /dev/null
@@ -1,65 +0,0 @@
-package io.newgrounds.objects;
-
-class Session extends Object {
-
- /** If true, the session_id is expired. Use App.startSession to get a new one.*/
- public var expired(default, null):Bool;
-
- /** A unique session identifier */
- public var id(default, null):String;
-
- /** If the session has no associated user but is not expired, this property will provide a URL that can be used to sign the user in. */
- public var passportUrl(default, null):String;
-
- /** If true, the user would like you to remember their session id. */
- public var remember(default, null):Bool;
-
- /** If the user has not signed in, or granted access to your app, this will be null */
- public var user(default, null):User;
-
- //TODO:desciption
- public var status(get, never):SessionStatus;
-
- public function new(core:NGLite, data:Dynamic = null) { super(core, data); }
-
- override public function parse(data:Dynamic):Void {
-
- id = data.id;
- expired = data.expired;
- passportUrl = data.passport_url;
- remember = data.remember;
-
- // --- KEEP THE SAME INSTANCE
- if (user == null)
- user = data.user;
- // TODO?: update original user instance with new data. (probly not)
-
- super.parse(data);
- }
-
- public function get_status():SessionStatus {
-
- if (expired || id == null || id == "")
- return SessionStatus.SESSION_EXPIRED;
-
- if (user != null && user.name != null && user.name != "")
- return SessionStatus.USER_LOADED;
-
- return SessionStatus.REQUEST_LOGIN;
- }
-
- public function expire():Void {
-
- expired = true;
- id = null;
- user = null;
- }
-}
-
-@:enum
-abstract SessionStatus(String) {
-
- var SESSION_EXPIRED = "session-expired";
- var REQUEST_LOGIN = "request-login";
- var USER_LOADED = "user-loaded";
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/objects/User.hx b/source/io/newgrounds/objects/User.hx
deleted file mode 100644
index 1ff7ce0..0000000
--- a/source/io/newgrounds/objects/User.hx
+++ /dev/null
@@ -1,19 +0,0 @@
-package io.newgrounds.objects;
-
-typedef User = {
-
- /** The user's icon images. */
- var icons:UserIcons;
-
- /** The user's numeric ID. */
- var id:Int;
-
- /** The user's textual name. */
- var name:String;
-
- /** Returns true if the user has a Newgrounds Supporter upgrade. */
- var supporter:Bool;
-
- /** The user's NG profile url. */
- var url:String;
-}
diff --git a/source/io/newgrounds/objects/UserIcons.hx b/source/io/newgrounds/objects/UserIcons.hx
deleted file mode 100644
index b5e56b2..0000000
--- a/source/io/newgrounds/objects/UserIcons.hx
+++ /dev/null
@@ -1,14 +0,0 @@
-package io.newgrounds.objects;
-
-typedef UserIcons = {
-
- /**The URL of the user's large icon. */
- var large:String;
-
- /** The URL of the user's medium icon. */
- var medium:String;
-
- /** The URL of the user's small icon. */
- var small:String;
-}
-
diff --git a/source/io/newgrounds/objects/events/Response.hx b/source/io/newgrounds/objects/events/Response.hx
deleted file mode 100644
index 107dc2b..0000000
--- a/source/io/newgrounds/objects/events/Response.hx
+++ /dev/null
@@ -1,43 +0,0 @@
-package io.newgrounds.objects.events;
-
-import io.newgrounds.objects.events.Result.ResultBase;
-import haxe.Json;
-import io.newgrounds.objects.Error;
-
-typedef DebugResponse = {
-
- var exec_time:Int;
- var input:Dynamic;
-}
-
-class Response {
-
- public var success(default, null):Bool;
- public var error(default, null):Error;
- public var debug(default, null):DebugResponse;
- public var result(default, null):Result;
-
- public function new (core:NGLite, reply:String) {
-
- var data:Dynamic;
-
- try {
- data = Json.parse(reply);
-
- } catch (e:Dynamic) {
-
- data = Json.parse('{"success":false,"error":{"message":"${Std.string(reply)}","code":0}}');
- }
-
- success = data.success;
- debug = data.debug;
-
- if (!success) {
- error = new Error(data.error.message, data.error.code);
- core.logError('Call unseccessful: $error');
- return;
- }
-
- result = new Result(core, data.result);
- }
-}
diff --git a/source/io/newgrounds/objects/events/Result.hx b/source/io/newgrounds/objects/events/Result.hx
deleted file mode 100644
index eaf8726..0000000
--- a/source/io/newgrounds/objects/events/Result.hx
+++ /dev/null
@@ -1,109 +0,0 @@
-package io.newgrounds.objects.events;
-
-class Result {
-
- public var echo(default, null):String;
- public var component(default, null):String;
-
- public var data(default, null):T;
- public var success(default, null):Bool;
- public var debug(default, null):Bool;
- public var error(default, null):Error;
-
- public function new(core:NGLite, data:Dynamic) {
-
- echo = data.echo;
- component = data.component;
-
- data = data.data;
- success = data.success;
- debug = data.debug;
-
- if(!data.success) {
-
- error = new Error(data.error.message, data.error.code);
- core.logError('$component fail: $error');
-
- } else
- this.data = data;
- }
-}
-
-typedef ResultBase = { };
-
-typedef SessionResult = {
- > ResultBase,
-
- var session:Dynamic;
-}
-
-typedef GetHostResult = {
- > ResultBase,
-
- var host_approved:Bool;
-}
-
-typedef GetCurrentVersionResult = {
- > ResultBase,
-
- var current_version:String;
- var client_deprecated:Bool;
-}
-
-typedef LogEventResult = {
- > ResultBase,
-
- var event_name:String;
-}
-
-typedef GetDateTimeResult = {
- > ResultBase,
-
- var datetime:String;
-}
-
-typedef GetVersionResult = {
- > ResultBase,
-
- var version:String;
-}
-
-typedef PingResult = {
- > ResultBase,
-
- var pong:String;
-}
-
-typedef MedalListResult = {
- > ResultBase,
-
- var medals:Array;
-}
-
-typedef MedalUnlockResult = {
- > ResultBase,
-
- var medal_score:String;
- var medal:Dynamic;
-}
-
-typedef ScoreBoardResult = {
- > ResultBase,
-
- var scoreboards:Array;
-}
-
-typedef ScoreResult = {
- > ResultBase,
-
- var scores:Array;
- var scoreboard:Dynamic;
-}
-
-typedef PostScoreResult = {
- > ResultBase,
-
- var tag:String;
- var scoreboard:Dynamic;
- var score:Score;
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/swf/LoadingBar.hx b/source/io/newgrounds/swf/LoadingBar.hx
deleted file mode 100644
index 9c7c590..0000000
--- a/source/io/newgrounds/swf/LoadingBar.hx
+++ /dev/null
@@ -1,23 +0,0 @@
-package io.newgrounds.swf;
-
-import openfl.display.MovieClip;
-
-class LoadingBar extends MovieClip {
-
- public var bar(default, null):MovieClip;
-
- public function new() {
- super();
-
- setProgress(0.0);
- }
-
- /**
- *
- * @param value The ratio of bytes loaded to bytes total
- */
- public function setProgress(value:Float):Void {
-
- bar.gotoAndStop(1 + Std.int(value * (bar.totalFrames - 1)));
- }
-}
diff --git a/source/io/newgrounds/swf/MedalPopup.hx b/source/io/newgrounds/swf/MedalPopup.hx
deleted file mode 100644
index f55ef42..0000000
--- a/source/io/newgrounds/swf/MedalPopup.hx
+++ /dev/null
@@ -1,151 +0,0 @@
-package io.newgrounds.swf;
-
-import io.newgrounds.swf.common.BaseAsset;
-import io.newgrounds.objects.Medal;
-
-import openfl.text.TextFieldAutoSize;
-import openfl.text.TextField;
-import openfl.display.DisplayObject;
-import openfl.display.Loader;
-import openfl.display.MovieClip;
-import openfl.net.URLRequest;
-import openfl.events.Event;
-
-class MedalPopup extends BaseAsset {
-
- static inline var FRAME_HIDDEN:String = "hidden";
- static inline var FRAME_MEDAL_UNLOCKED:String = "medalUnlocked";
- static inline var FRAME_INTRO_COMPLETE:String = "introComplete";
- static inline var FRAME_UNLOCK_COMPLETE:String = "unlockComplete";
- static inline var MIN_TEXT_SIZE:Int = 12;
-
- public var medalIcon(default, null):MovieClip;
- public var medalName(default, null):MovieClip;
- public var medalPoints(default, null):MovieClip;
-
- public var alwaysOnTop:Bool;
- #if !ng_lite
- public var requiresSession:Bool;
- #end
-
- var _animQueue = new ArrayVoid>();
- var _scrollSpeed:Float;
-
- public function new() {
- super();
-
- mouseEnabled = false;
- mouseChildren = false;
-
- hide();
- addFrameScript(totalFrames - 1, onUnlockAnimComplete);
- }
-
- function hide():Void {
-
- visible = false;
- gotoAndStop(FRAME_HIDDEN);
- }
-
- #if !ng_lite
- override function onReady():Void {
- super.onReady();
-
- if (NG.core.medals != null)
- onMedalsLoaded();
- else
- NG.core.onLogin.addOnce(NG.core.requestMedals.bind(onMedalsLoaded));
- }
-
- function onMedalsLoaded():Void {
-
- for (medal in NG.core.medals)
- medal.onUnlock.add(onMedalOnlock.bind(medal));
- }
-
- function onMedalOnlock(medal:Medal):Void {
-
- if (requiresSession && !NG.core.loggedIn)
- return;
-
- var loader = new Loader();
- loader.load(new URLRequest(medal.icon));
-
- playAnim(loader, medal.name, medal.value);
- }
-
- #end
-
- public function playAnim(icon:DisplayObject, name:String, value:Int):Void {
-
- if (currentLabel == FRAME_HIDDEN)
- playNextAnim(icon, name, value);
- else
- _animQueue.push(playNextAnim.bind(icon, name, value));
- }
-
- function playNextAnim(icon:DisplayObject, name:String, value:Int):Void {
-
- visible = true;
- gotoAndPlay(FRAME_MEDAL_UNLOCKED);
-
- if (alwaysOnTop && parent != null) {
-
- parent.setChildIndex(this, parent.numChildren - 1);
- }
-
- while(medalIcon.numChildren > 0)
- medalIcon.removeChildAt(0);
-
- cast(medalPoints.getChildByName("field"), TextField).text = Std.string(value);
-
- var field:TextField = cast medalName.getChildByName("field");
- field.autoSize = TextFieldAutoSize.LEFT;
- field.x = 0;
- field.text = "";
- var oldWidth = medalName.width;
- field.text = name;
-
- _scrollSpeed = 0;
- if (field.width > oldWidth + 4) {
-
- field.x = oldWidth + 4;
- initScroll(field);
- }
-
- medalIcon.addChild(icon);
- }
-
- function initScroll(field:TextField):Void {
- //TODO: Find out why scrollrect didn't work
-
- var animDuration = 0;
-
- for (frame in currentLabels){
-
- if (frame.name == FRAME_INTRO_COMPLETE )
- animDuration -= frame.frame;
- else if (frame.name == FRAME_UNLOCK_COMPLETE)
- animDuration += frame.frame;
- }
-
- _scrollSpeed = (field.width + field.x + 4) / animDuration;
- field.addEventListener(Event.ENTER_FRAME, updateScroll);
- }
-
- function updateScroll(e:Event):Void{
-
- if (currentLabel == FRAME_INTRO_COMPLETE)
- cast (e.currentTarget, TextField).x -= _scrollSpeed;
- }
-
- function onUnlockAnimComplete():Void {
-
- cast (medalName.getChildByName("field"), TextField).removeEventListener(Event.ENTER_FRAME, updateScroll);
-
- if (_animQueue.length == 0)
- hide();
- else
- (_animQueue.shift())();
- }
-}
diff --git a/source/io/newgrounds/swf/ScoreBrowser.hx b/source/io/newgrounds/swf/ScoreBrowser.hx
deleted file mode 100644
index c4232c2..0000000
--- a/source/io/newgrounds/swf/ScoreBrowser.hx
+++ /dev/null
@@ -1,250 +0,0 @@
-package io.newgrounds.swf;
-
-import openfl.events.Event;
-import io.newgrounds.swf.common.DropDown;
-import io.newgrounds.objects.Score;
-import io.newgrounds.objects.events.Result.ScoreBoardResult;
-import io.newgrounds.objects.events.Result.ScoreResult;
-import io.newgrounds.objects.events.Response;
-import io.newgrounds.swf.common.BaseAsset;
-import io.newgrounds.swf.common.Button;
-import io.newgrounds.components.ScoreBoardComponent.Period;
-
-import openfl.display.MovieClip;
-import openfl.text.TextField;
-
-class ScoreBrowser extends BaseAsset {
-
- public var prevButton (default, null):MovieClip;
- public var nextButton (default, null):MovieClip;
- public var reloadButton (default, null):MovieClip;
- public var listBox (default, null):MovieClip;
- public var loadingIcon (default, null):MovieClip;
- public var errorIcon (default, null):MovieClip;
- public var scoreContainer(default, null):MovieClip;
- public var titleField (default, null):TextField;
- public var pageField (default, null):TextField;
-
- public var period(get, set):Period;
- function get_period():Period { return _periodDropDown.value; }
- function set_period(value:Period):Period { return _periodDropDown.value = value; }
-
- public var title(get, set):String;
- function get_title():String { return titleField.text; }
- function set_title(value:String):String { return titleField.text = value; }
-
- public var tag(default, set):String;
- function set_tag(value:String):String {
-
- if (this.tag != value) {
-
- this.tag = value;
- delayReload();
- }
-
- return value;
- }
-
- public var social(default, set):Bool;
- function set_social(value:Bool):Bool {
-
- if (this.social != value) {
-
- this.social = value;
- delayReload();
- }
-
- return value;
- }
-
- public var boardId(default, set):Int;
- function set_boardId(value:Int):Int {
-
- _boardIDSet = true;
-
- if (this.boardId != value) {
-
- this.boardId = value;
- delayReload();
- }
-
- return value;
- }
-
- public var page(default, set):Int;
- function set_page(value:Int):Int {
-
- if (this.page != value) {
-
- this.page = value;
- delayReload();
- }
-
- return value;
- }
-
- var _scores:Array;
- var _limit:Int = 0;
- var _periodDropDown:DropDown;
- var _boardIDSet:Bool;
-
- public function new() { super(); }
-
- override function setDefaults():Void {
- super.setDefaults();
-
- boardId = -1;
- _boardIDSet = false;
-
- scoreContainer.visible = false;
- loadingIcon.visible = false;
- reloadButton.visible = false;
- errorIcon.visible = false;
- errorIcon.addFrameScript(errorIcon.totalFrames - 1, errorIcon.stop);
-
- //TODO: prevent memory leaks?
- new Button(prevButton, onPrevClick);
- new Button(nextButton, onNextClick);
- new Button(reloadButton, reload);
- _periodDropDown = new DropDown(listBox, delayReload);
- _periodDropDown.addItem("Current day" , Period.DAY );
- _periodDropDown.addItem("Current week" , Period.WEEK );
- _periodDropDown.addItem("Current month", Period.MONTH);
- _periodDropDown.addItem("Current year" , Period.YEAR );
- _periodDropDown.addItem("All time" , Period.ALL );
- _periodDropDown.value = Period.ALL;
-
- _scores = new Array();
- while(true) {
-
- var score:MovieClip = cast scoreContainer.getChildByName('score${_scores.length}');
- if (score == null)
- break;
-
- new Button(score);
- _scores.push(score);
- }
-
- _limit = _scores.length;
- }
-
- override function onReady():Void {
- super.onReady();
-
- if (boardId == -1 && !_boardIDSet) {
-
- #if ng_lite
- NG.core.calls.scoreBoard.getBoards()
- .addDataHandler(onBoardsRecieved)
- .queue();
- #else
- if (NG.core.scoreBoards != null)
- onBoardsLoaded();
- else
- NG.core.requestScoreBoards(onBoardsLoaded);
- #end
- }
-
- reload();
- }
-
- #if ng_lite
- function onBoardsRecieved(response:Response):Void {
-
- if (response.success && response.result.success) {
-
- for (board in response.result.data.scoreboards) {
-
- NG.core.log('No boardId specified defaulting to ${board.name}');
- boardId = board.id;
- return;
- }
- }
- }
- #else
- function onBoardsLoaded():Void {
-
- for (board in NG.core.scoreBoards) {
-
- NG.core.log('No boardId specified defaulting to ${board.name}');
- boardId = board.id;
- return;
- }
- }
- #end
-
- /** Used internally to avoid multiple server requests from various property changes in a small time-frame. **/
- function delayReload():Void {
-
- addEventListener(Event.EXIT_FRAME, onDelayComplete);
- }
-
- function onDelayComplete(e:Event):Void { reload(); }
-
- public function reload():Void {
- removeEventListener(Event.EXIT_FRAME, onDelayComplete);
-
- errorIcon.visible = false;
- scoreContainer.visible = false;
- pageField.text = 'page ${page + 1}';
-
- if (_coreReady && boardId != -1 && _limit > 0 && period != null) {
-
- loadingIcon.visible = true;
-
- NG.core.calls.scoreBoard.getScores(boardId, _limit, _limit * page, period, social, tag)
- .addDataHandler(onScoresReceive)
- .send();
- }
- }
-
- function onScoresReceive(response:Response):Void {
-
- loadingIcon.visible = false;
-
- if (response.success && response.result.success) {
-
- scoreContainer.visible = true;
-
- var i = _limit;
- while(i > 0) {
- i--;
-
- if (i < response.result.data.scores.length)
- drawScore(i, response.result.data.scores[i], _scores[i]);
- else
- drawScore(i, null, _scores[i]);
- }
-
- } else {
-
- errorIcon.visible = true;
- errorIcon.gotoAndPlay(1);
- reloadButton.visible = true;
- }
- }
-
- inline function drawScore(rank:Int, score:Score, asset:MovieClip):Void {
-
- if (score == null)
- asset.visible = false;
- else {
-
- asset.visible = true;
- cast (asset.getChildByName("nameField" ), TextField).text = score.user.name;
- cast (asset.getChildByName("scoreField"), TextField).text = score.formatted_value;
- cast (asset.getChildByName("rankField" ), TextField).text = Std.string(rank + 1);
- }
- }
-
- function onPrevClick():Void {
-
- if (page > 0)
- page--;
- }
-
- function onNextClick():Void {
-
- page++;
- }
-}
diff --git a/source/io/newgrounds/swf/common/BaseAsset.hx b/source/io/newgrounds/swf/common/BaseAsset.hx
deleted file mode 100644
index da1f612..0000000
--- a/source/io/newgrounds/swf/common/BaseAsset.hx
+++ /dev/null
@@ -1,35 +0,0 @@
-package io.newgrounds.swf.common;
-
-import openfl.events.Event;
-import openfl.display.MovieClip;
-
-class BaseAsset extends MovieClip {
-
- var _coreReady:Bool = false;
-
- public function new() {
- super();
-
- setDefaults();
-
- if (stage != null)
- onAdded(null);
- else
- addEventListener(Event.ADDED_TO_STAGE, onAdded);
- }
-
- function setDefaults():Void { }
-
- function onAdded(e:Event):Void {
-
- if (NG.core != null)
- onReady();
- else
- NG.onCoreReady.add(onReady);
- }
-
- function onReady():Void {
-
- _coreReady = true;
- }
-}
diff --git a/source/io/newgrounds/swf/common/Button.hx b/source/io/newgrounds/swf/common/Button.hx
deleted file mode 100644
index 5f46175..0000000
--- a/source/io/newgrounds/swf/common/Button.hx
+++ /dev/null
@@ -1,151 +0,0 @@
-package io.newgrounds.swf.common;
-
-import openfl.display.Stage;
-import openfl.events.Event;
-import openfl.events.MouseEvent;
-import openfl.display.MovieClip;
-
-class Button {
-
- var _enabled:Bool;
- public var enabled(get, set):Bool;
- function get_enabled():Bool { return _enabled; }
- function set_enabled(value:Bool):Bool {
-
- if (value != _enabled) {
-
- _enabled = value;
- updateEnabled();
- }
-
- return value;
- }
-
- public var onClick:Void->Void;
- public var onOver:Void->Void;
- public var onOut:Void->Void;
-
- var _target:MovieClip;
- var _down:Bool;
- var _over:Bool;
- var _foundLabels:Array;
-
- public function new(target:MovieClip, onClick:Void->Void = null, onOver:Void->Void = null, onOut:Void->Void = null) {
-
- _target = target;
- this.onClick = onClick;
- this.onOver = onOver;
- this.onOut = onOut;
-
- _foundLabels = new Array();
- for (label in _target.currentLabels)
- _foundLabels.push(label.name);
-
- _target.stop();
- _target.addEventListener(Event.ADDED_TO_STAGE, onAdded);
- if (target.stage != null)
- onAdded(null);
-
- enabled = true;
- }
-
- function onAdded(e:Event):Void {
-
- var stage = _target.stage;
- stage.addEventListener(MouseEvent.MOUSE_UP, mouseHandler);
- _target.addEventListener(MouseEvent.MOUSE_OVER, mouseHandler);
- _target.addEventListener(MouseEvent.MOUSE_OUT, mouseHandler);
- _target.addEventListener(MouseEvent.MOUSE_DOWN, mouseHandler);
- _target.addEventListener(MouseEvent.CLICK, mouseHandler);
-
- function selfRemoveEvent(e:Event):Void {
-
- _target.removeEventListener(Event.REMOVED_FROM_STAGE, selfRemoveEvent);
- onRemove(e, stage);
- }
- _target.addEventListener(Event.REMOVED_FROM_STAGE, selfRemoveEvent);
- }
-
- function onRemove(e:Event, stage:Stage):Void {
-
- stage.removeEventListener(MouseEvent.MOUSE_UP, mouseHandler);
- _target.removeEventListener(MouseEvent.MOUSE_OVER, mouseHandler);
- _target.removeEventListener(MouseEvent.MOUSE_OUT, mouseHandler);
- _target.removeEventListener(MouseEvent.MOUSE_DOWN, mouseHandler);
- _target.removeEventListener(MouseEvent.CLICK, mouseHandler);
- }
-
- function mouseHandler(event:MouseEvent):Void {
-
- switch(event.type) {
-
- case MouseEvent.MOUSE_OVER:
-
- _over = true;
-
- if (onOver != null)
- onOver();
-
- case MouseEvent.MOUSE_OUT:
-
- _over = false;
-
- if (onOut != null)
- onOut();
-
- case MouseEvent.MOUSE_DOWN:
-
- _down = true;
-
- case MouseEvent.MOUSE_UP:
-
- _down = false;
-
- case MouseEvent.CLICK:
-
- if (enabled && onClick != null)
- onClick();
- }
- updateState();
- }
-
- function updateEnabled():Void {
-
- updateState();
-
- _target.useHandCursor = enabled;
- _target.buttonMode = enabled;
- }
-
- function updateState():Void {
-
- var state = determineState();
-
- if (_target.currentLabel != state && _foundLabels.indexOf(state) != -1)
- _target.gotoAndStop(state);
- }
-
- function determineState():String {
-
- if (enabled) {
-
- if (_over)
- return _down ? "down" : "over";
-
- return "up";
-
- }
- return "disabled";
- }
-
- public function destroy():Void {
-
- _target.removeEventListener(Event.ADDED_TO_STAGE, onAdded);
-
- _target = null;
- onClick = null;
- onOver = null;
- onOut = null;
- _foundLabels = null;
- }
-}
diff --git a/source/io/newgrounds/swf/common/DropDown.hx b/source/io/newgrounds/swf/common/DropDown.hx
deleted file mode 100644
index a882cf3..0000000
--- a/source/io/newgrounds/swf/common/DropDown.hx
+++ /dev/null
@@ -1,88 +0,0 @@
-package io.newgrounds.swf.common;
-
-
-import haxe.ds.StringMap;
-
-import openfl.display.MovieClip;
-import openfl.display.Sprite;
-import openfl.text.TextField;
-
-class DropDown {
-
- public var value(default, set):String;
- function set_value(v:String):String {
-
- if (this.value == v)
- return v;
-
- this.value = v;
- _selectedLabel.text = _values.get(v);
-
- if (_onChange != null)
- _onChange();
-
- return v;
- }
-
- var _choiceContainer:Sprite;
- var _selectedLabel:TextField;
- var _onChange:Void->Void;
- var _values:StringMap;
- var _unusedChoices:Array;
-
- public function new(target:MovieClip, label:String = "", onChange:Void->Void = null) {
-
- _onChange = onChange;
-
- _selectedLabel = cast cast(target.getChildByName("currentItem"), MovieClip).getChildByName("label");
- _selectedLabel.text = label;
-
- _values = new StringMap();
-
- new Button(cast target.getChildByName("button"), onClickExpand);
- new Button(cast target.getChildByName("currentItem"), onClickExpand);
- _choiceContainer = new Sprite();
- _choiceContainer.visible = false;
- target.addChild(_choiceContainer);
-
- _unusedChoices = new Array();
- while(true) {
-
- var item:MovieClip = cast target.getChildByName('item${_unusedChoices.length}');
- if (item == null)
- break;
-
- target.removeChild(item);
- _unusedChoices.push(item);
- }
- }
-
- public function addItem(name:String, value:String):Void {
-
- _values.set(value, name);
-
- if (_unusedChoices.length == 0) {
-
- NG.core.logError('cannot create another dropBox item max=${_choiceContainer.numChildren}');
- return;
- }
-
- var button = _unusedChoices.shift();
- cast(button.getChildByName("label"), TextField).text = name;
- _choiceContainer.addChild(button);
-
- new Button(button, onChoiceClick.bind(value));
- }
-
- function onClickExpand():Void {
-
- _choiceContainer.visible = !_choiceContainer.visible;
- }
-
- function onChoiceClick(name:String):Void {
-
- value = name;
-
- _choiceContainer.visible = false;
- }
-}
\ No newline at end of file
diff --git a/source/io/newgrounds/utils/AsyncHttp.hx b/source/io/newgrounds/utils/AsyncHttp.hx
deleted file mode 100644
index 4fbe143..0000000
--- a/source/io/newgrounds/utils/AsyncHttp.hx
+++ /dev/null
@@ -1,203 +0,0 @@
-package io.newgrounds.utils;
-
-import io.newgrounds.NGLite;
-
-import haxe.Http;
-import haxe.Timer;
-
-#if neko
-import neko.vm.Thread;
-#elseif java
-import java.vm.Thread;
-#elseif cpp
-import cpp.vm.Thread;
-#end
-
-/**
- * Uses Threading to turn hxcpp's synchronous http requests into asynchronous processes
- *
- * @author GeoKureli
- */
-class AsyncHttp {
-
- inline static var PATH:String = "https://newgrounds.io/gateway_v3.php";
-
- static public function send
- ( core:NGLite
- , data:String
- , onData:String->Void
- , onError:String->Void
- , onStatus:Int->Void
- ) {
-
- core.logVerbose('sending: $data');
-
- #if (neko || java || cpp)
- sendAsync(core, data, onData, onError, onStatus);
- #else
- sendSync(core, data, onData, onError, onStatus);
- #end
- }
-
- static function sendSync
- ( core:NGLite
- , data:String
- , onData:String->Void
- , onError:String->Void
- , onStatus:Int->Void
- ):Void {
-
- var http = new Http(PATH);
- http.setParameter("input", data);
- http.onData = onData;
- http.onError = onError;
- http.onStatus = onStatus;
- // #if js http.async = async; #end
- http.request(true);
- }
-
- #if (neko || java || cpp)
- static var _deadPool:Array = [];
- static var _livePool:Array = [];
- static var _map:Map = new Map();
- static var _timer:Timer;
-
- static var _count:Int = 0;
-
- var _core:NGLite;
- var _key:Int;
- var _onData:String->Void;
- var _onError:String->Void;
- var _onStatus:Int->Void;
- var _worker:Thread;
-
- public function new (core:NGLite) {
-
- _core = core;
- _worker = Thread.create(sendThreaded);
- _key = _count++;
- _map[_key] = this;
- _core.logVerbose('async http created: $_key');
- }
-
- function start(data:String, onData:String->Void, onError:String->Void, onStatus:Int->Void) {
-
- _core.logVerbose('async http started: $_key');
-
- if (_livePool.length == 0)
- startTimer();
-
- _deadPool.remove(this);
- _livePool.push(this);
-
- _onData = onData;
- _onError = onError;
- _onStatus = onStatus;
- _worker.sendMessage({ source:Thread.current(), args:data, key:_key, core:_core });
- }
-
- function handleMessage(data:ReplyData):Void {
-
- _core.logVerbose('handling message: $_key');
-
- if (data.status != null) {
-
- _core.logVerbose('\t- status: ${data.status}');
- _onStatus(cast data.status);
- return;
- }
-
- var tempFunc:Void->Void;
- if (data.data != null) {
-
- _core.logVerbose('\t- data');
- tempFunc = _onData.bind(data.data);
-
- } else {
-
- _core.logVerbose('\t- error');
- tempFunc = _onError.bind(data.error);
- }
-
- cleanUp();
- // Delay the call until destroy so that we're more likely to use a single
- // thread on daisy-chained calls
- tempFunc();
- }
-
- inline function cleanUp():Void {
-
- _onData = null;
- _onError = null;
-
- _deadPool.push(this);
- _livePool.remove(this);
-
- if (_livePool.length == 0)
- stopTimer();
- }
-
- static function sendAsync
- ( core:NGLite
- , data:String
- , onData:String->Void
- , onError:String->Void
- , onStatus:Int->Void
- ):Void {
-
- var http:AsyncHttp;
- if (_deadPool.length == 0)
- http = new AsyncHttp(core);
- else
- http = _deadPool[0];
-
- http.start(data, onData, onError, onStatus);
- }
-
- static function startTimer():Void {
-
- if (_timer != null)
- return;
-
- _timer = new Timer(1000 / 60.0);
- _timer.run = update;
- }
-
- static function stopTimer():Void {
-
- _timer.stop();
- _timer = null;
- }
-
- static public function update():Void {
-
- var message:ReplyData = cast Thread.readMessage(false);
- if (message != null)
- _map[message.key].handleMessage(message);
- }
-
- static function sendThreaded():Void {
-
- while(true) {
-
- var data:LoaderData = cast Thread.readMessage(true);
- data.core.logVerbose('start message received: ${data.key}');
-
- sendSync
- ( data.core
- , data.args
- , function(reply ) { data.source.sendMessage({ key:data.key, data :reply }); }
- , function(error ) { data.source.sendMessage({ key:data.key, error :error }); }
- , function(status) { data.source.sendMessage({ key:data.key, status:status }); }
- );
- }
- }
-
- #end
-}
-
-
-#if (neko || java || cpp)
-typedef LoaderData = { source:Thread, key:Int, args:String, core:NGLite };
-typedef ReplyData = { key:Int, ?data:String, ?error:String, ?status:Null };
-#end
\ No newline at end of file
diff --git a/source/io/newgrounds/utils/Dispatcher.hx b/source/io/newgrounds/utils/Dispatcher.hx
deleted file mode 100644
index 699da01..0000000
--- a/source/io/newgrounds/utils/Dispatcher.hx
+++ /dev/null
@@ -1,118 +0,0 @@
-package io.newgrounds.utils;
-
-/**
- * Basically shitty signals, but I didn't want to have external references.
-**/
-class Dispatcher {
-
- var _list:ArrayVoid>;
- var _once:ArrayVoid>;
-
- public function new() {
-
- _list = new ArrayVoid>();
- _once = new ArrayVoid>();
- }
-
- public function add(handler:Void->Void, once:Bool = false):Bool {
-
- if (_list.indexOf(handler) != -1) {
-
- // ---- REMOVE ONCE
- if (!once && _once.indexOf(handler) != -1)
- _once.remove(handler);
-
- return false;
- }
-
- _list.unshift(handler);
- if (once)
- _once.unshift(handler);
-
- return true;
- }
-
- inline public function addOnce(handler:Void->Void):Bool {
-
- return add(handler, true);
- }
-
- public function remove(handler:Void->Void):Bool {
-
- _once.remove(handler);
- return _list.remove(handler);
- }
-
- public function dispatch():Void {
-
- var i = _list.length - 1;
- while(i >= 0) {
-
- var handler = _list[i];
-
- if (_once.remove(handler))
- _list.remove(handler);
-
- handler();
-
- i--;
- }
- }
-}
-
-class TypedDispatcher {
-
- var _list:ArrayVoid>;
- var _once:ArrayVoid>;
-
- public function new() {
-
- _list = new ArrayVoid>();
- _once = new ArrayVoid>();
- }
-
- public function add(handler:T->Void, once:Bool = false):Bool {
-
- if (_list.indexOf(handler) != -1) {
-
- // ---- REMOVE ONCE
- if (!once && _once.indexOf(handler) != -1)
- _once.remove(handler);
-
- return false;
- }
-
- _list.unshift(handler);
- if (once)
- _once.unshift(handler);
-
- return true;
- }
-
- inline public function addOnce(handler:T->Void):Bool {
-
- return add(handler, true);
- }
-
- public function remove(handler:T->Void):Bool {
-
- _once.remove(handler);
- return _list.remove(handler);
- }
-
- public function dispatch(arg:T):Void {
-
- var i = _list.length - 1;
- while(i >= 0) {
-
- var handler = _list[i];
-
- if (_once.remove(handler))
- _list.remove(handler);
-
- handler(arg);
-
- i--;
- }
- }
-}
\ No newline at end of file