init commit
This commit is contained in:
commit
322d1a0516
1054 changed files with 85998 additions and 0 deletions
1159
source/editors/CharacterEditorState.hx
Normal file
1159
source/editors/CharacterEditorState.hx
Normal file
File diff suppressed because it is too large
Load diff
2195
source/editors/ChartingState.hx
Normal file
2195
source/editors/ChartingState.hx
Normal file
File diff suppressed because it is too large
Load diff
779
source/editors/DialogueCharacterEditorState.hx
Normal file
779
source/editors/DialogueCharacterEditorState.hx
Normal file
|
@ -0,0 +1,779 @@
|
|||
package editors;
|
||||
|
||||
#if desktop
|
||||
import Discord.DiscordClient;
|
||||
#end
|
||||
import flixel.FlxG;
|
||||
import flixel.FlxSprite;
|
||||
import flixel.addons.display.FlxGridOverlay;
|
||||
import flixel.addons.transition.FlxTransitionableState;
|
||||
import flixel.group.FlxGroup.FlxTypedGroup;
|
||||
import flixel.math.FlxMath;
|
||||
import flixel.text.FlxText;
|
||||
import flixel.util.FlxColor;
|
||||
import flixel.system.FlxSound;
|
||||
import flixel.addons.ui.FlxInputText;
|
||||
import flixel.addons.ui.FlxUI9SliceSprite;
|
||||
import flixel.addons.ui.FlxUI;
|
||||
import flixel.addons.ui.FlxUICheckBox;
|
||||
import flixel.addons.ui.FlxUIInputText;
|
||||
import flixel.addons.ui.FlxUINumericStepper;
|
||||
import flixel.addons.ui.FlxUITabMenu;
|
||||
import flixel.ui.FlxButton;
|
||||
import openfl.net.FileReference;
|
||||
import openfl.events.Event;
|
||||
import openfl.events.IOErrorEvent;
|
||||
import flash.net.FileFilter;
|
||||
import haxe.Json;
|
||||
import DialogueBoxPsych;
|
||||
import flixel.FlxCamera;
|
||||
import flixel.group.FlxSpriteGroup;
|
||||
import lime.system.Clipboard;
|
||||
#if sys
|
||||
import sys.io.File;
|
||||
#end
|
||||
|
||||
using StringTools;
|
||||
|
||||
class DialogueCharacterEditorState extends MusicBeatState
|
||||
{
|
||||
var box:FlxSprite;
|
||||
var daText:Alphabet = null;
|
||||
|
||||
private static var TIP_TEXT_MAIN:String =
|
||||
'JKLI - Move camera (Hold Shift to move 4x faster)
|
||||
\nQ/E - Zoom out/in
|
||||
\nR - Reset Camera
|
||||
\nH - Toggle Speech Bubble
|
||||
\nSpace - Reset text';
|
||||
|
||||
private static var TIP_TEXT_OFFSET:String =
|
||||
'JKLI - Move camera (Hold Shift to move 4x faster)
|
||||
\nQ/E - Zoom out/in
|
||||
\nR - Reset Camera
|
||||
\nH - Toggle Ghosts
|
||||
\nWASD - Move Looping animation offset (Red)
|
||||
\nArrow Keys - Move Idle/Finished animation offset (Blue)
|
||||
\nHold Shift to move offsets 10x faster';
|
||||
|
||||
var tipText:FlxText;
|
||||
var offsetLoopText:FlxText;
|
||||
var offsetIdleText:FlxText;
|
||||
|
||||
var camGame:FlxCamera;
|
||||
var camOther:FlxCamera;
|
||||
|
||||
var mainGroup:FlxSpriteGroup;
|
||||
var hudGroup:FlxSpriteGroup;
|
||||
|
||||
var character:DialogueCharacter;
|
||||
var ghostLoop:DialogueCharacter;
|
||||
var ghostIdle:DialogueCharacter;
|
||||
|
||||
override function create() {
|
||||
persistentUpdate = persistentDraw = true;
|
||||
camGame = new FlxCamera();
|
||||
camOther = new FlxCamera();
|
||||
camGame.bgColor = FlxColor.fromHSL(0, 0, 0.5);
|
||||
camOther.bgColor.alpha = 0;
|
||||
|
||||
FlxG.cameras.reset(camGame);
|
||||
FlxG.cameras.add(camOther);
|
||||
FlxCamera.defaultCameras = [camOther];
|
||||
|
||||
mainGroup = new FlxSpriteGroup();
|
||||
mainGroup.cameras = [camGame];
|
||||
hudGroup = new FlxSpriteGroup();
|
||||
hudGroup.cameras = [camGame];
|
||||
add(mainGroup);
|
||||
add(hudGroup);
|
||||
|
||||
character = new DialogueCharacter();
|
||||
character.scrollFactor.set();
|
||||
mainGroup.add(character);
|
||||
|
||||
ghostLoop = new DialogueCharacter();
|
||||
ghostLoop.alpha = 0;
|
||||
ghostLoop.color = FlxColor.RED;
|
||||
ghostLoop.isGhost = true;
|
||||
ghostLoop.jsonFile = character.jsonFile;
|
||||
ghostLoop.cameras = [camGame];
|
||||
add(ghostLoop);
|
||||
|
||||
ghostIdle = new DialogueCharacter();
|
||||
ghostIdle.alpha = 0;
|
||||
ghostIdle.color = FlxColor.BLUE;
|
||||
ghostIdle.isGhost = true;
|
||||
ghostIdle.jsonFile = character.jsonFile;
|
||||
ghostIdle.cameras = [camGame];
|
||||
add(ghostIdle);
|
||||
|
||||
box = new FlxSprite(70, 370);
|
||||
box.frames = Paths.getSparrowAtlas('speech_bubble');
|
||||
box.scrollFactor.set();
|
||||
box.antialiasing = ClientPrefs.globalAntialiasing;
|
||||
box.animation.addByPrefix('normal', 'speech bubble normal', 24);
|
||||
box.animation.addByPrefix('center', 'speech bubble middle', 24);
|
||||
box.animation.play('normal', true);
|
||||
box.setGraphicSize(Std.int(box.width * 0.9));
|
||||
box.updateHitbox();
|
||||
hudGroup.add(box);
|
||||
|
||||
tipText = new FlxText(10, 10, FlxG.width - 20, TIP_TEXT_MAIN, 8);
|
||||
tipText.setFormat(Paths.font("vcr.ttf"), 16, FlxColor.WHITE, RIGHT, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK);
|
||||
tipText.cameras = [camOther];
|
||||
tipText.scrollFactor.set();
|
||||
add(tipText);
|
||||
|
||||
offsetLoopText = new FlxText(10, 10, 0, '', 32);
|
||||
offsetLoopText.setFormat(Paths.font("vcr.ttf"), 32, FlxColor.WHITE, LEFT, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK);
|
||||
offsetLoopText.cameras = [camOther];
|
||||
offsetLoopText.scrollFactor.set();
|
||||
add(offsetLoopText);
|
||||
offsetLoopText.visible = false;
|
||||
|
||||
offsetIdleText = new FlxText(10, 46, 0, '', 32);
|
||||
offsetIdleText.setFormat(Paths.font("vcr.ttf"), 32, FlxColor.WHITE, LEFT, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK);
|
||||
offsetIdleText.cameras = [camOther];
|
||||
offsetIdleText.scrollFactor.set();
|
||||
add(offsetIdleText);
|
||||
offsetIdleText.visible = false;
|
||||
|
||||
reloadCharacter();
|
||||
updateTextBox();
|
||||
reloadText();
|
||||
|
||||
addEditorBox();
|
||||
FlxG.mouse.visible = true;
|
||||
updateCharTypeBox();
|
||||
|
||||
super.create();
|
||||
}
|
||||
|
||||
var UI_typebox:FlxUITabMenu;
|
||||
var UI_mainbox:FlxUITabMenu;
|
||||
function addEditorBox() {
|
||||
var tabs = [
|
||||
{name: 'Character Type', label: 'Character Type'},
|
||||
];
|
||||
UI_typebox = new FlxUITabMenu(null, tabs, true);
|
||||
UI_typebox.resize(120, 180);
|
||||
UI_typebox.x = 900;
|
||||
UI_typebox.y = FlxG.height - UI_typebox.height - 50;
|
||||
UI_typebox.scrollFactor.set();
|
||||
UI_typebox.camera = camGame;
|
||||
addTypeUI();
|
||||
add(UI_typebox);
|
||||
|
||||
var tabs = [
|
||||
{name: 'Animations', label: 'Animations'},
|
||||
{name: 'Character', label: 'Character'},
|
||||
];
|
||||
UI_mainbox = new FlxUITabMenu(null, tabs, true);
|
||||
UI_mainbox.resize(200, 250);
|
||||
UI_mainbox.x = UI_typebox.x + UI_typebox.width;
|
||||
UI_mainbox.y = FlxG.height - UI_mainbox.height - 50;
|
||||
UI_mainbox.scrollFactor.set();
|
||||
UI_mainbox.camera = camGame;
|
||||
addAnimationsUI();
|
||||
addCharacterUI();
|
||||
add(UI_mainbox);
|
||||
UI_mainbox.selected_tab_id = 'Character';
|
||||
lastTab = UI_mainbox.selected_tab_id;
|
||||
}
|
||||
|
||||
var leftCheckbox:FlxUICheckBox;
|
||||
var centerCheckbox:FlxUICheckBox;
|
||||
var rightCheckbox:FlxUICheckBox;
|
||||
function addTypeUI() {
|
||||
var tab_group = new FlxUI(null, UI_typebox);
|
||||
tab_group.name = "Character Type";
|
||||
|
||||
leftCheckbox = new FlxUICheckBox(10, 20, null, null, "Left", 100);
|
||||
leftCheckbox.callback = function()
|
||||
{
|
||||
character.jsonFile.dialogue_pos = 'left';
|
||||
updateCharTypeBox();
|
||||
};
|
||||
|
||||
centerCheckbox = new FlxUICheckBox(leftCheckbox.x, leftCheckbox.y + 40, null, null, "Center", 100);
|
||||
centerCheckbox.callback = function()
|
||||
{
|
||||
character.jsonFile.dialogue_pos = 'center';
|
||||
updateCharTypeBox();
|
||||
};
|
||||
|
||||
rightCheckbox = new FlxUICheckBox(centerCheckbox.x, centerCheckbox.y + 40, null, null, "Right", 100);
|
||||
rightCheckbox.callback = function()
|
||||
{
|
||||
character.jsonFile.dialogue_pos = 'right';
|
||||
updateCharTypeBox();
|
||||
};
|
||||
|
||||
tab_group.add(leftCheckbox);
|
||||
tab_group.add(centerCheckbox);
|
||||
tab_group.add(rightCheckbox);
|
||||
UI_typebox.addGroup(tab_group);
|
||||
}
|
||||
|
||||
var curSelectedAnim:String;
|
||||
var animationArray:Array<String> = [];
|
||||
var animationDropDown:FlxUIDropDownMenuCustom;
|
||||
var animationInputText:FlxUIInputText;
|
||||
var loopInputText:FlxUIInputText;
|
||||
var idleInputText:FlxUIInputText;
|
||||
function addAnimationsUI() {
|
||||
var tab_group = new FlxUI(null, UI_mainbox);
|
||||
tab_group.name = "Animations";
|
||||
|
||||
animationDropDown = new FlxUIDropDownMenuCustom(10, 30, FlxUIDropDownMenuCustom.makeStrIdLabelArray([''], true), function(animation:String) {
|
||||
var anim:String = animationArray[Std.parseInt(animation)];
|
||||
if(character.dialogueAnimations.exists(anim)) {
|
||||
ghostLoop.playAnim(anim);
|
||||
ghostIdle.playAnim(anim, true);
|
||||
|
||||
curSelectedAnim = anim;
|
||||
var animShit:DialogueAnimArray = character.dialogueAnimations.get(curSelectedAnim);
|
||||
offsetLoopText.text = 'Loop: ' + animShit.loop_offsets;
|
||||
offsetIdleText.text = 'Idle: ' + animShit.idle_offsets;
|
||||
|
||||
animationInputText.text = animShit.anim;
|
||||
loopInputText.text = animShit.loop_name;
|
||||
idleInputText.text = animShit.idle_name;
|
||||
}
|
||||
});
|
||||
|
||||
animationInputText = new FlxUIInputText(15, 85, 80, '', 8);
|
||||
blockPressWhileTypingOn.push(animationInputText);
|
||||
loopInputText = new FlxUIInputText(animationInputText.x, animationInputText.y + 35, 150, '', 8);
|
||||
blockPressWhileTypingOn.push(loopInputText);
|
||||
idleInputText = new FlxUIInputText(loopInputText.x, loopInputText.y + 40, 150, '', 8);
|
||||
blockPressWhileTypingOn.push(idleInputText);
|
||||
|
||||
var addUpdateButton:FlxButton = new FlxButton(10, idleInputText.y + 30, "Add/Update", function() {
|
||||
var theAnim:String = animationInputText.text.trim();
|
||||
if(character.dialogueAnimations.exists(theAnim)) //Update
|
||||
{
|
||||
for (i in 0...character.jsonFile.animations.length) {
|
||||
var animArray:DialogueAnimArray = character.jsonFile.animations[i];
|
||||
if(animArray.anim.trim() == theAnim) {
|
||||
animArray.loop_name = loopInputText.text;
|
||||
animArray.idle_name = idleInputText.text;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
character.reloadAnimations();
|
||||
ghostLoop.reloadAnimations();
|
||||
ghostIdle.reloadAnimations();
|
||||
if(curSelectedAnim == theAnim) {
|
||||
ghostLoop.playAnim(theAnim);
|
||||
ghostIdle.playAnim(theAnim, true);
|
||||
}
|
||||
}
|
||||
else //Add
|
||||
{
|
||||
var newAnim:DialogueAnimArray = {
|
||||
anim: theAnim,
|
||||
loop_name: loopInputText.text,
|
||||
loop_offsets: [0, 0],
|
||||
idle_name: idleInputText.text,
|
||||
idle_offsets: [0, 0]
|
||||
}
|
||||
character.jsonFile.animations.push(newAnim);
|
||||
|
||||
var lastSelected:String = animationDropDown.selectedLabel;
|
||||
character.reloadAnimations();
|
||||
ghostLoop.reloadAnimations();
|
||||
ghostIdle.reloadAnimations();
|
||||
reloadAnimationsDropDown();
|
||||
animationDropDown.selectedLabel = lastSelected;
|
||||
}
|
||||
});
|
||||
|
||||
var removeUpdateButton:FlxButton = new FlxButton(100, addUpdateButton.y, "Remove", function() {
|
||||
for (i in 0...character.jsonFile.animations.length) {
|
||||
var animArray:DialogueAnimArray = character.jsonFile.animations[i];
|
||||
if(animArray != null && animArray.anim.trim() == animationInputText.text.trim()) {
|
||||
var lastSelected:String = animationDropDown.selectedLabel;
|
||||
character.jsonFile.animations.remove(animArray);
|
||||
character.reloadAnimations();
|
||||
ghostLoop.reloadAnimations();
|
||||
ghostIdle.reloadAnimations();
|
||||
reloadAnimationsDropDown();
|
||||
if(character.jsonFile.animations.length > 0 && lastSelected == animArray.anim.trim()) {
|
||||
var animToPlay:String = character.jsonFile.animations[0].anim;
|
||||
ghostLoop.playAnim(animToPlay);
|
||||
ghostIdle.playAnim(animToPlay, true);
|
||||
}
|
||||
animationDropDown.selectedLabel = lastSelected;
|
||||
animationInputText.text = '';
|
||||
loopInputText.text = '';
|
||||
idleInputText.text = '';
|
||||
break;
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
tab_group.add(new FlxText(animationDropDown.x, animationDropDown.y - 18, 0, 'Animations:'));
|
||||
tab_group.add(new FlxText(animationInputText.x, animationInputText.y - 18, 0, 'Animation name:'));
|
||||
tab_group.add(new FlxText(loopInputText.x, loopInputText.y - 18, 0, 'Loop name on .XML file:'));
|
||||
tab_group.add(new FlxText(idleInputText.x, idleInputText.y - 18, 0, 'Idle/Finished name on .XML file:'));
|
||||
tab_group.add(animationInputText);
|
||||
tab_group.add(loopInputText);
|
||||
tab_group.add(idleInputText);
|
||||
tab_group.add(addUpdateButton);
|
||||
tab_group.add(removeUpdateButton);
|
||||
tab_group.add(animationDropDown);
|
||||
UI_mainbox.addGroup(tab_group);
|
||||
reloadAnimationsDropDown();
|
||||
}
|
||||
|
||||
function reloadAnimationsDropDown() {
|
||||
animationArray = [];
|
||||
for (anim in character.jsonFile.animations) {
|
||||
animationArray.push(anim.anim);
|
||||
}
|
||||
|
||||
if(animationArray.length < 1) animationArray = [''];
|
||||
animationDropDown.setData(FlxUIDropDownMenuCustom.makeStrIdLabelArray(animationArray, true));
|
||||
}
|
||||
|
||||
var imageInputText:FlxUIInputText;
|
||||
var scaleStepper:FlxUINumericStepper;
|
||||
var xStepper:FlxUINumericStepper;
|
||||
var yStepper:FlxUINumericStepper;
|
||||
var blockPressWhileTypingOn:Array<FlxUIInputText> = [];
|
||||
function addCharacterUI() {
|
||||
var tab_group = new FlxUI(null, UI_mainbox);
|
||||
tab_group.name = "Character";
|
||||
|
||||
imageInputText = new FlxUIInputText(10, 30, 80, character.jsonFile.image, 8);
|
||||
blockPressWhileTypingOn.push(imageInputText);
|
||||
xStepper = new FlxUINumericStepper(imageInputText.x, imageInputText.y + 50, 10, character.jsonFile.position[0], -2000, 2000, 0);
|
||||
yStepper = new FlxUINumericStepper(imageInputText.x + 80, xStepper.y, 10, character.jsonFile.position[1], -2000, 2000, 0);
|
||||
scaleStepper = new FlxUINumericStepper(imageInputText.x, xStepper.y + 50, 0.05, character.jsonFile.scale, 0.1, 10, 2);
|
||||
|
||||
tab_group.add(new FlxText(10, imageInputText.y - 18, 0, 'Image file name:'));
|
||||
tab_group.add(new FlxText(10, xStepper.y - 18, 0, 'Position Offset:'));
|
||||
tab_group.add(new FlxText(10, scaleStepper.y - 18, 0, 'Scale:'));
|
||||
tab_group.add(imageInputText);
|
||||
tab_group.add(xStepper);
|
||||
tab_group.add(yStepper);
|
||||
tab_group.add(scaleStepper);
|
||||
|
||||
var reloadImageButton:FlxButton = new FlxButton(10, scaleStepper.y + 60, "Reload Image", function() {
|
||||
reloadCharacter();
|
||||
});
|
||||
|
||||
var loadButton:FlxButton = new FlxButton(reloadImageButton.x + 100, reloadImageButton.y, "Load Character", function() {
|
||||
loadCharacter();
|
||||
});
|
||||
var saveButton:FlxButton = new FlxButton(loadButton.x, reloadImageButton.y - 30, "Save Character", function() {
|
||||
saveCharacter();
|
||||
});
|
||||
tab_group.add(reloadImageButton);
|
||||
tab_group.add(loadButton);
|
||||
tab_group.add(saveButton);
|
||||
UI_mainbox.addGroup(tab_group);
|
||||
}
|
||||
|
||||
function updateCharTypeBox() {
|
||||
leftCheckbox.checked = false;
|
||||
centerCheckbox.checked = false;
|
||||
rightCheckbox.checked = false;
|
||||
|
||||
switch(character.jsonFile.dialogue_pos) {
|
||||
case 'left':
|
||||
leftCheckbox.checked = true;
|
||||
case 'center':
|
||||
centerCheckbox.checked = true;
|
||||
case 'right':
|
||||
rightCheckbox.checked = true;
|
||||
}
|
||||
reloadCharacter();
|
||||
updateTextBox();
|
||||
}
|
||||
|
||||
private static var DEFAULT_TEXT:String = 'Lorem ipsum dolor sit amet';
|
||||
function reloadText() {
|
||||
if(daText != null) {
|
||||
daText.killTheTimer();
|
||||
daText.kill();
|
||||
hudGroup.remove(daText);
|
||||
daText.destroy();
|
||||
}
|
||||
daText = new Alphabet(0, 0, DEFAULT_TEXT, false, true, 0.05, 0.7);
|
||||
daText.x = DialogueBoxPsych.DEFAULT_TEXT_X;
|
||||
daText.y = DialogueBoxPsych.DEFAULT_TEXT_Y;
|
||||
hudGroup.add(daText);
|
||||
}
|
||||
|
||||
function reloadCharacter() {
|
||||
var charsArray:Array<DialogueCharacter> = [character, ghostLoop, ghostIdle];
|
||||
for (char in charsArray) {
|
||||
char.frames = Paths.getSparrowAtlas('dialogue/' + character.jsonFile.image);
|
||||
char.jsonFile = character.jsonFile;
|
||||
char.reloadAnimations();
|
||||
char.setGraphicSize(Std.int(char.width * DialogueCharacter.DEFAULT_SCALE * character.jsonFile.scale));
|
||||
char.updateHitbox();
|
||||
}
|
||||
character.x = DialogueBoxPsych.LEFT_CHAR_X;
|
||||
character.y = DialogueBoxPsych.DEFAULT_CHAR_Y;
|
||||
|
||||
switch(character.jsonFile.dialogue_pos) {
|
||||
case 'right':
|
||||
character.x = FlxG.width - character.width + DialogueBoxPsych.RIGHT_CHAR_X;
|
||||
|
||||
case 'center':
|
||||
character.x = FlxG.width / 2;
|
||||
character.x -= character.width / 2;
|
||||
}
|
||||
character.x += character.jsonFile.position[0] + mainGroup.x;
|
||||
character.y += character.jsonFile.position[1] + mainGroup.y;
|
||||
character.playAnim(); //Plays random animation
|
||||
if(character.jsonFile.animations.length > 0) {
|
||||
curSelectedAnim = character.jsonFile.animations[0].anim;
|
||||
var animShit:DialogueAnimArray = character.dialogueAnimations.get(curSelectedAnim);
|
||||
ghostLoop.playAnim(animShit.anim);
|
||||
ghostIdle.playAnim(animShit.anim, true);
|
||||
offsetLoopText.text = 'Loop: ' + animShit.loop_offsets;
|
||||
offsetIdleText.text = 'Idle: ' + animShit.idle_offsets;
|
||||
}
|
||||
|
||||
#if desktop
|
||||
// Updating Discord Rich Presence
|
||||
DiscordClient.changePresence("Dialogue Character Editor", "Editting: " + character.jsonFile.image);
|
||||
#end
|
||||
}
|
||||
|
||||
function updateTextBox() {
|
||||
box.flipX = false;
|
||||
var anim:String = 'normal';
|
||||
switch(character.jsonFile.dialogue_pos) {
|
||||
case 'left':
|
||||
box.flipX = true;
|
||||
case 'center':
|
||||
anim = 'center';
|
||||
}
|
||||
box.animation.play(anim, true);
|
||||
DialogueBoxPsych.updateBoxOffsets(box);
|
||||
}
|
||||
|
||||
override function getEvent(id:String, sender:Dynamic, data:Dynamic, ?params:Array<Dynamic>) {
|
||||
if(id == FlxUIInputText.CHANGE_EVENT && sender == imageInputText) {
|
||||
character.jsonFile.image = imageInputText.text;
|
||||
} else if(id == FlxUINumericStepper.CHANGE_EVENT && (sender is FlxUINumericStepper)) {
|
||||
if(sender == scaleStepper) {
|
||||
character.jsonFile.scale = scaleStepper.value;
|
||||
reloadCharacter();
|
||||
} else if(sender == xStepper) {
|
||||
character.jsonFile.position[0] = xStepper.value;
|
||||
reloadCharacter();
|
||||
} else if(sender == yStepper) {
|
||||
character.jsonFile.position[1] = yStepper.value;
|
||||
reloadCharacter();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var currentGhosts:Int = 0;
|
||||
var lastTab:String = 'Character';
|
||||
var transitioning:Bool = false;
|
||||
override function update(elapsed:Float) {
|
||||
if(transitioning) {
|
||||
super.update(elapsed);
|
||||
return;
|
||||
}
|
||||
|
||||
if(character.animation.curAnim != null) {
|
||||
if(daText.finishedText) {
|
||||
if(character.animationIsLoop()) {
|
||||
character.playAnim(character.animation.curAnim.name, true);
|
||||
}
|
||||
} else if(character.animation.curAnim.finished) {
|
||||
character.animation.curAnim.restart();
|
||||
}
|
||||
}
|
||||
|
||||
var blockInput:Bool = false;
|
||||
for (inputText in blockPressWhileTypingOn) {
|
||||
if(inputText.hasFocus) {
|
||||
FlxG.sound.muteKeys = [];
|
||||
FlxG.sound.volumeDownKeys = [];
|
||||
FlxG.sound.volumeUpKeys = [];
|
||||
blockInput = true;
|
||||
|
||||
if(FlxG.keys.pressed.CONTROL && FlxG.keys.justPressed.V && Clipboard.text != null) { //Copy paste
|
||||
inputText.text = ClipboardAdd(inputText.text);
|
||||
inputText.caretIndex = inputText.text.length;
|
||||
getEvent(FlxUIInputText.CHANGE_EVENT, inputText, null, []);
|
||||
}
|
||||
if(FlxG.keys.justPressed.ENTER) inputText.hasFocus = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if(!blockInput && !animationDropDown.dropPanel.visible) {
|
||||
FlxG.sound.muteKeys = TitleState.muteKeys;
|
||||
FlxG.sound.volumeDownKeys = TitleState.volumeDownKeys;
|
||||
FlxG.sound.volumeUpKeys = TitleState.volumeUpKeys;
|
||||
if(FlxG.keys.justPressed.SPACE && UI_mainbox.selected_tab_id == 'Character') {
|
||||
character.playAnim();
|
||||
updateTextBox();
|
||||
reloadText();
|
||||
}
|
||||
|
||||
//lots of Ifs lol get trolled
|
||||
var offsetAdd:Int = 1;
|
||||
var speed:Float = 300;
|
||||
if(FlxG.keys.pressed.SHIFT) {
|
||||
speed = 1200;
|
||||
offsetAdd = 10;
|
||||
}
|
||||
|
||||
var negaMult:Array<Int> = [1, 1, -1, -1];
|
||||
var controlArray:Array<Bool> = [FlxG.keys.pressed.J, FlxG.keys.pressed.I, FlxG.keys.pressed.L, FlxG.keys.pressed.K];
|
||||
for (i in 0...controlArray.length) {
|
||||
if(controlArray[i]) {
|
||||
if(i % 2 == 1) {
|
||||
mainGroup.y += speed * elapsed * negaMult[i];
|
||||
} else {
|
||||
mainGroup.x += speed * elapsed * negaMult[i];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if(UI_mainbox.selected_tab_id == 'Animations' && curSelectedAnim != null && character.dialogueAnimations.exists(curSelectedAnim)) {
|
||||
var moved:Bool = false;
|
||||
var animShit:DialogueAnimArray = character.dialogueAnimations.get(curSelectedAnim);
|
||||
var controlArrayLoop:Array<Bool> = [FlxG.keys.justPressed.A, FlxG.keys.justPressed.W, FlxG.keys.justPressed.D, FlxG.keys.justPressed.S];
|
||||
var controlArrayIdle:Array<Bool> = [FlxG.keys.justPressed.LEFT, FlxG.keys.justPressed.UP, FlxG.keys.justPressed.RIGHT, FlxG.keys.justPressed.DOWN];
|
||||
for (i in 0...controlArrayLoop.length) {
|
||||
if(controlArrayLoop[i]) {
|
||||
if(i % 2 == 1) {
|
||||
animShit.loop_offsets[1] += offsetAdd * negaMult[i];
|
||||
} else {
|
||||
animShit.loop_offsets[0] += offsetAdd * negaMult[i];
|
||||
}
|
||||
moved = true;
|
||||
}
|
||||
}
|
||||
for (i in 0...controlArrayIdle.length) {
|
||||
if(controlArrayIdle[i]) {
|
||||
if(i % 2 == 1) {
|
||||
animShit.idle_offsets[1] += offsetAdd * negaMult[i];
|
||||
} else {
|
||||
animShit.idle_offsets[0] += offsetAdd * negaMult[i];
|
||||
}
|
||||
moved = true;
|
||||
}
|
||||
}
|
||||
|
||||
if(moved) {
|
||||
offsetLoopText.text = 'Loop: ' + animShit.loop_offsets;
|
||||
offsetIdleText.text = 'Idle: ' + animShit.idle_offsets;
|
||||
ghostLoop.offset.set(animShit.loop_offsets[0], animShit.loop_offsets[1]);
|
||||
ghostIdle.offset.set(animShit.idle_offsets[0], animShit.idle_offsets[1]);
|
||||
}
|
||||
}
|
||||
|
||||
if (FlxG.keys.pressed.Q && camGame.zoom > 0.1) {
|
||||
camGame.zoom -= elapsed * camGame.zoom;
|
||||
if(camGame.zoom < 0.1) camGame.zoom = 0.1;
|
||||
}
|
||||
if (FlxG.keys.pressed.E && camGame.zoom < 1) {
|
||||
camGame.zoom += elapsed * camGame.zoom;
|
||||
if(camGame.zoom > 1) camGame.zoom = 1;
|
||||
}
|
||||
if(FlxG.keys.justPressed.H) {
|
||||
if(UI_mainbox.selected_tab_id == 'Animations') {
|
||||
currentGhosts++;
|
||||
if(currentGhosts > 2) currentGhosts = 0;
|
||||
|
||||
ghostLoop.visible = (currentGhosts != 1);
|
||||
ghostIdle.visible = (currentGhosts != 2);
|
||||
ghostLoop.alpha = (currentGhosts == 2 ? 1 : 0.6);
|
||||
ghostIdle.alpha = (currentGhosts == 1 ? 1 : 0.6);
|
||||
} else {
|
||||
hudGroup.visible = !hudGroup.visible;
|
||||
}
|
||||
}
|
||||
if(FlxG.keys.justPressed.R) {
|
||||
camGame.zoom = 1;
|
||||
mainGroup.setPosition(0, 0);
|
||||
hudGroup.visible = true;
|
||||
}
|
||||
|
||||
if(UI_mainbox.selected_tab_id != lastTab) {
|
||||
if(UI_mainbox.selected_tab_id == 'Animations') {
|
||||
hudGroup.alpha = 0;
|
||||
mainGroup.alpha = 0;
|
||||
ghostLoop.alpha = 0.6;
|
||||
ghostIdle.alpha = 0.6;
|
||||
tipText.text = TIP_TEXT_OFFSET;
|
||||
offsetLoopText.visible = true;
|
||||
offsetIdleText.visible = true;
|
||||
currentGhosts = 0;
|
||||
|
||||
} else {
|
||||
hudGroup.alpha = 1;
|
||||
mainGroup.alpha = 1;
|
||||
ghostLoop.alpha = 0;
|
||||
ghostIdle.alpha = 0;
|
||||
tipText.text = TIP_TEXT_MAIN;
|
||||
offsetLoopText.visible = false;
|
||||
offsetIdleText.visible = false;
|
||||
character.playAnim();
|
||||
updateTextBox();
|
||||
reloadText();
|
||||
}
|
||||
lastTab = UI_mainbox.selected_tab_id;
|
||||
currentGhosts = 0;
|
||||
}
|
||||
|
||||
if(FlxG.keys.justPressed.ESCAPE) {
|
||||
MusicBeatState.switchState(new editors.MasterEditorMenu());
|
||||
FlxG.sound.playMusic(Paths.music('freakyMenu'), 1);
|
||||
transitioning = true;
|
||||
}
|
||||
|
||||
ghostLoop.setPosition(character.x, character.y);
|
||||
ghostIdle.setPosition(character.x, character.y);
|
||||
hudGroup.x = mainGroup.x;
|
||||
hudGroup.y = mainGroup.y;
|
||||
}
|
||||
super.update(elapsed);
|
||||
}
|
||||
|
||||
var _file:FileReference = null;
|
||||
function loadCharacter() {
|
||||
var jsonFilter:FileFilter = new FileFilter('JSON', 'json');
|
||||
_file = new FileReference();
|
||||
_file.addEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.addEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.addEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
_file.browse([jsonFilter]);
|
||||
}
|
||||
|
||||
function onLoadComplete(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
|
||||
#if sys
|
||||
var fullPath:String = null;
|
||||
var jsonLoaded = cast Json.parse(Json.stringify(_file)); //Exploit(???) for accessing a private variable
|
||||
if(jsonLoaded.__path != null) fullPath = jsonLoaded.__path; //I'm either a genious or dangerously dumb
|
||||
|
||||
if(fullPath != null) {
|
||||
var rawJson:String = File.getContent(fullPath);
|
||||
if(rawJson != null) {
|
||||
var loadedChar:DialogueCharacterFile = cast Json.parse(rawJson);
|
||||
if(loadedChar.dialogue_pos != null) //Make sure it's really a dialogue character
|
||||
{
|
||||
var cutName:String = _file.name.substr(0, _file.name.length - 5);
|
||||
trace("Successfully loaded file: " + cutName);
|
||||
character.jsonFile = loadedChar;
|
||||
reloadCharacter();
|
||||
reloadAnimationsDropDown();
|
||||
updateCharTypeBox();
|
||||
updateTextBox();
|
||||
reloadText();
|
||||
imageInputText.text = character.jsonFile.image;
|
||||
scaleStepper.value = character.jsonFile.scale;
|
||||
xStepper.value = character.jsonFile.position[0];
|
||||
yStepper.value = character.jsonFile.position[1];
|
||||
_file = null;
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
_file = null;
|
||||
#else
|
||||
trace("File couldn't be loaded! You aren't on Desktop, are you?");
|
||||
#end
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the save file dialog is cancelled.
|
||||
*/
|
||||
function onLoadCancel(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
_file = null;
|
||||
trace("Cancelled file loading.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Called if there is an error while saving the gameplay recording.
|
||||
*/
|
||||
function onLoadError(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
_file = null;
|
||||
trace("Problem loading file");
|
||||
}
|
||||
|
||||
function saveCharacter() {
|
||||
var data:String = Json.stringify(character.jsonFile, "\t");
|
||||
if (data.length > 0)
|
||||
{
|
||||
var splittedImage:Array<String> = imageInputText.text.trim().split('_');
|
||||
var characterName:String = splittedImage[0].toLowerCase().replace(' ', '');
|
||||
|
||||
_file = new FileReference();
|
||||
_file.addEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.addEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.addEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file.save(data, characterName + ".json");
|
||||
}
|
||||
}
|
||||
|
||||
function onSaveComplete(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file = null;
|
||||
FlxG.log.notice("Successfully saved file.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the save file dialog is cancelled.
|
||||
*/
|
||||
function onSaveCancel(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file = null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Called if there is an error while saving the gameplay recording.
|
||||
*/
|
||||
function onSaveError(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file = null;
|
||||
FlxG.log.error("Problem saving file");
|
||||
}
|
||||
|
||||
function ClipboardAdd(prefix:String = ''):String {
|
||||
if(prefix.toLowerCase().endsWith('v')) //probably copy paste attempt
|
||||
{
|
||||
prefix = prefix.substring(0, prefix.length-1);
|
||||
}
|
||||
|
||||
var text:String = prefix + Clipboard.text.replace('\n', '');
|
||||
return text;
|
||||
}
|
||||
}
|
546
source/editors/DialogueEditorState.hx
Normal file
546
source/editors/DialogueEditorState.hx
Normal file
|
@ -0,0 +1,546 @@
|
|||
package editors;
|
||||
|
||||
#if desktop
|
||||
import Discord.DiscordClient;
|
||||
#end
|
||||
import flixel.FlxG;
|
||||
import flixel.FlxSprite;
|
||||
import flixel.addons.display.FlxGridOverlay;
|
||||
import flixel.addons.transition.FlxTransitionableState;
|
||||
import flixel.group.FlxGroup.FlxTypedGroup;
|
||||
import flixel.math.FlxMath;
|
||||
import flixel.text.FlxText;
|
||||
import flixel.util.FlxColor;
|
||||
import flixel.system.FlxSound;
|
||||
import flixel.addons.ui.FlxInputText;
|
||||
import flixel.addons.ui.FlxUI9SliceSprite;
|
||||
import flixel.addons.ui.FlxUI;
|
||||
import flixel.addons.ui.FlxUICheckBox;
|
||||
import flixel.addons.ui.FlxUIInputText;
|
||||
import flixel.addons.ui.FlxUINumericStepper;
|
||||
import flixel.addons.ui.FlxUITabMenu;
|
||||
import flixel.ui.FlxButton;
|
||||
import openfl.net.FileReference;
|
||||
import openfl.events.Event;
|
||||
import openfl.events.IOErrorEvent;
|
||||
import flash.net.FileFilter;
|
||||
import haxe.Json;
|
||||
import DialogueBoxPsych;
|
||||
import lime.system.Clipboard;
|
||||
#if sys
|
||||
import sys.io.File;
|
||||
#end
|
||||
|
||||
using StringTools;
|
||||
|
||||
class DialogueEditorState extends MusicBeatState
|
||||
{
|
||||
var character:DialogueCharacter;
|
||||
var box:FlxSprite;
|
||||
var daText:Alphabet;
|
||||
|
||||
var selectedText:FlxText;
|
||||
var animText:FlxText;
|
||||
|
||||
var defaultLine:DialogueLine;
|
||||
var dialogueFile:DialogueFile = null;
|
||||
|
||||
override function create() {
|
||||
persistentUpdate = persistentDraw = true;
|
||||
FlxG.camera.bgColor = FlxColor.fromHSL(0, 0, 0.5);
|
||||
|
||||
defaultLine = {
|
||||
portrait: DialogueCharacter.DEFAULT_CHARACTER,
|
||||
expression: 'talk',
|
||||
text: DEFAULT_TEXT,
|
||||
boxState: DEFAULT_BUBBLETYPE,
|
||||
speed: 0.05
|
||||
};
|
||||
|
||||
dialogueFile = {
|
||||
dialogue: [
|
||||
copyDefaultLine()
|
||||
]
|
||||
};
|
||||
|
||||
character = new DialogueCharacter();
|
||||
character.scrollFactor.set();
|
||||
add(character);
|
||||
|
||||
box = new FlxSprite(70, 370);
|
||||
box.frames = Paths.getSparrowAtlas('speech_bubble');
|
||||
box.scrollFactor.set();
|
||||
box.antialiasing = ClientPrefs.globalAntialiasing;
|
||||
box.animation.addByPrefix('normal', 'speech bubble normal', 24);
|
||||
box.animation.addByPrefix('angry', 'AHH speech bubble', 24);
|
||||
box.animation.addByPrefix('center', 'speech bubble middle', 24);
|
||||
box.animation.addByPrefix('center-angry', 'AHH Speech Bubble middle', 24);
|
||||
box.animation.play('normal', true);
|
||||
box.setGraphicSize(Std.int(box.width * 0.9));
|
||||
box.updateHitbox();
|
||||
add(box);
|
||||
|
||||
addEditorBox();
|
||||
FlxG.mouse.visible = true;
|
||||
|
||||
var addLineText:FlxText = new FlxText(10, 10, FlxG.width - 20, 'Press O to remove the current dialogue line, Press P to add another line after the current one.', 8);
|
||||
addLineText.setFormat(Paths.font("vcr.ttf"), 16, FlxColor.WHITE, LEFT, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK);
|
||||
addLineText.scrollFactor.set();
|
||||
add(addLineText);
|
||||
|
||||
selectedText = new FlxText(10, 32, FlxG.width - 20, '', 8);
|
||||
selectedText.setFormat(Paths.font("vcr.ttf"), 24, FlxColor.WHITE, LEFT, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK);
|
||||
selectedText.scrollFactor.set();
|
||||
add(selectedText);
|
||||
|
||||
animText = new FlxText(10, 62, FlxG.width - 20, '', 8);
|
||||
animText.setFormat(Paths.font("vcr.ttf"), 24, FlxColor.WHITE, LEFT, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK);
|
||||
animText.scrollFactor.set();
|
||||
add(animText);
|
||||
changeText();
|
||||
super.create();
|
||||
}
|
||||
|
||||
var UI_box:FlxUITabMenu;
|
||||
function addEditorBox() {
|
||||
var tabs = [
|
||||
{name: 'Dialogue Line', label: 'Dialogue Line'},
|
||||
];
|
||||
UI_box = new FlxUITabMenu(null, tabs, true);
|
||||
UI_box.resize(250, 190);
|
||||
UI_box.x = FlxG.width - UI_box.width - 10;
|
||||
UI_box.y = 10;
|
||||
UI_box.scrollFactor.set();
|
||||
UI_box.alpha = 0.8;
|
||||
addDialogueLineUI();
|
||||
add(UI_box);
|
||||
}
|
||||
|
||||
var characterInputText:FlxUIInputText;
|
||||
var lineInputText:FlxUIInputText;
|
||||
var angryCheckbox:FlxUICheckBox;
|
||||
var speedStepper:FlxUINumericStepper;
|
||||
function addDialogueLineUI() {
|
||||
var tab_group = new FlxUI(null, UI_box);
|
||||
tab_group.name = "Dialogue Line";
|
||||
|
||||
characterInputText = new FlxUIInputText(10, 20, 80, DialogueCharacter.DEFAULT_CHARACTER, 8);
|
||||
blockPressWhileTypingOn.push(characterInputText);
|
||||
|
||||
speedStepper = new FlxUINumericStepper(10, characterInputText.y + 40, 0.005, 0.05, 0, 0.5, 3);
|
||||
|
||||
angryCheckbox = new FlxUICheckBox(speedStepper.x + 120, speedStepper.y, null, null, "Angry Textbox", 200);
|
||||
angryCheckbox.callback = function()
|
||||
{
|
||||
updateTextBox();
|
||||
dialogueFile.dialogue[curSelected].boxState = (angryCheckbox.checked ? 'angry' : 'normal');
|
||||
};
|
||||
|
||||
lineInputText = new FlxUIInputText(10, speedStepper.y + 45, 200, DEFAULT_TEXT, 8);
|
||||
blockPressWhileTypingOn.push(lineInputText);
|
||||
|
||||
var loadButton:FlxButton = new FlxButton(20, lineInputText.y + 30, "Load Dialogue", function() {
|
||||
loadDialogue();
|
||||
});
|
||||
var saveButton:FlxButton = new FlxButton(loadButton.x + 120, loadButton.y, "Save Dialogue", function() {
|
||||
saveDialogue();
|
||||
});
|
||||
|
||||
tab_group.add(new FlxText(10, speedStepper.y - 18, 0, 'Interval/Speed (ms):'));
|
||||
tab_group.add(new FlxText(10, characterInputText.y - 18, 0, 'Character:'));
|
||||
tab_group.add(new FlxText(10, lineInputText.y - 18, 0, 'Text:'));
|
||||
tab_group.add(characterInputText);
|
||||
tab_group.add(angryCheckbox);
|
||||
tab_group.add(speedStepper);
|
||||
tab_group.add(lineInputText);
|
||||
tab_group.add(lineInputText);
|
||||
tab_group.add(loadButton);
|
||||
tab_group.add(saveButton);
|
||||
UI_box.addGroup(tab_group);
|
||||
}
|
||||
|
||||
function copyDefaultLine():DialogueLine {
|
||||
var copyLine:DialogueLine = {
|
||||
portrait: defaultLine.portrait,
|
||||
expression: defaultLine.expression,
|
||||
text: defaultLine.text,
|
||||
boxState: defaultLine.boxState,
|
||||
speed: defaultLine.speed
|
||||
};
|
||||
return copyLine;
|
||||
}
|
||||
|
||||
function updateTextBox() {
|
||||
box.flipX = false;
|
||||
var isAngry:Bool = angryCheckbox.checked;
|
||||
var anim:String = isAngry ? 'angry' : 'normal';
|
||||
|
||||
switch(character.jsonFile.dialogue_pos) {
|
||||
case 'left':
|
||||
box.flipX = true;
|
||||
case 'center':
|
||||
if(isAngry) {
|
||||
anim = 'center-angry';
|
||||
} else {
|
||||
anim = 'center';
|
||||
}
|
||||
}
|
||||
box.animation.play(anim, true);
|
||||
DialogueBoxPsych.updateBoxOffsets(box);
|
||||
}
|
||||
|
||||
function reloadCharacter() {
|
||||
character.frames = Paths.getSparrowAtlas('dialogue/' + character.jsonFile.image);
|
||||
character.jsonFile = character.jsonFile;
|
||||
character.reloadAnimations();
|
||||
character.setGraphicSize(Std.int(character.width * DialogueCharacter.DEFAULT_SCALE * character.jsonFile.scale));
|
||||
character.updateHitbox();
|
||||
character.x = DialogueBoxPsych.LEFT_CHAR_X;
|
||||
character.y = DialogueBoxPsych.DEFAULT_CHAR_Y;
|
||||
|
||||
switch(character.jsonFile.dialogue_pos) {
|
||||
case 'right':
|
||||
character.x = FlxG.width - character.width + DialogueBoxPsych.RIGHT_CHAR_X;
|
||||
|
||||
case 'center':
|
||||
character.x = FlxG.width / 2;
|
||||
character.x -= character.width / 2;
|
||||
}
|
||||
character.x += character.jsonFile.position[0];
|
||||
character.y += character.jsonFile.position[1];
|
||||
character.playAnim(); //Plays random animation
|
||||
characterAnimSpeed();
|
||||
|
||||
if(character.animation.curAnim != null) {
|
||||
animText.text = 'Animation: ' + character.jsonFile.animations[curAnim].anim + ' (' + (curAnim + 1) +' / ' + character.jsonFile.animations.length + ') - Press W or S to scroll';
|
||||
} else {
|
||||
animText.text = 'ERROR! NO ANIMATIONS FOUND';
|
||||
}
|
||||
}
|
||||
|
||||
private static var DEFAULT_TEXT:String = "coolswag";
|
||||
private static var DEFAULT_SPEED:Float = 0.05;
|
||||
private static var DEFAULT_BUBBLETYPE:String = "normal";
|
||||
function reloadText(speed:Float = 0.05) {
|
||||
if(daText != null) {
|
||||
daText.killTheTimer();
|
||||
daText.kill();
|
||||
remove(daText);
|
||||
daText.destroy();
|
||||
}
|
||||
|
||||
if(Math.isNaN(speed) || speed < 0.001) speed = 0.0;
|
||||
|
||||
var textToType:String = lineInputText.text;
|
||||
if(textToType == null || textToType.length < 1) textToType = ' ';
|
||||
daText = new Alphabet(DialogueBoxPsych.DEFAULT_TEXT_X, DialogueBoxPsych.DEFAULT_TEXT_Y, textToType, false, true, speed, 0.7);
|
||||
add(daText);
|
||||
|
||||
if(speed > 0) {
|
||||
if(character.jsonFile.animations.length > curAnim && character.jsonFile.animations[curAnim] != null) {
|
||||
character.playAnim(character.jsonFile.animations[curAnim].anim);
|
||||
}
|
||||
characterAnimSpeed();
|
||||
}
|
||||
|
||||
#if desktop
|
||||
// Updating Discord Rich Presence
|
||||
var rpcText:String = lineInputText.text;
|
||||
if(rpcText == null || rpcText.length < 1) rpcText = '(Empty)';
|
||||
if(rpcText.length < 3) rpcText += ' '; //Fixes a bug on RPC that triggers an error when the text is too short
|
||||
DiscordClient.changePresence("Dialogue Editor", rpcText);
|
||||
#end
|
||||
}
|
||||
|
||||
override function getEvent(id:String, sender:Dynamic, data:Dynamic, ?params:Array<Dynamic>) {
|
||||
if(id == FlxUIInputText.CHANGE_EVENT && (sender is FlxUIInputText)) {
|
||||
if(sender == characterInputText) {
|
||||
character.reloadCharacterJson(characterInputText.text);
|
||||
reloadCharacter();
|
||||
updateTextBox();
|
||||
|
||||
if(character.jsonFile.animations.length > 0) {
|
||||
curAnim = 0;
|
||||
if(character.jsonFile.animations.length > curAnim && character.jsonFile.animations[curAnim] != null) {
|
||||
character.playAnim(character.jsonFile.animations[curAnim].anim, daText.finishedText);
|
||||
animText.text = 'Animation: ' + character.jsonFile.animations[curAnim].anim + ' (' + (curAnim + 1) +' / ' + character.jsonFile.animations.length + ') - Press W or S to scroll';
|
||||
} else {
|
||||
animText.text = 'ERROR! NO ANIMATIONS FOUND';
|
||||
}
|
||||
characterAnimSpeed();
|
||||
}
|
||||
dialogueFile.dialogue[curSelected].portrait = characterInputText.text;
|
||||
} else if(sender == lineInputText) {
|
||||
reloadText(0);
|
||||
dialogueFile.dialogue[curSelected].text = lineInputText.text;
|
||||
}
|
||||
} else if(id == FlxUINumericStepper.CHANGE_EVENT && (sender == speedStepper)) {
|
||||
reloadText(speedStepper.value);
|
||||
dialogueFile.dialogue[curSelected].speed = speedStepper.value;
|
||||
if(Math.isNaN(dialogueFile.dialogue[curSelected].speed) || dialogueFile.dialogue[curSelected].speed == null || dialogueFile.dialogue[curSelected].speed < 0.001) {
|
||||
dialogueFile.dialogue[curSelected].speed = 0.0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var curSelected:Int = 0;
|
||||
var curAnim:Int = 0;
|
||||
var blockPressWhileTypingOn:Array<FlxUIInputText> = [];
|
||||
var transitioning:Bool = false;
|
||||
override function update(elapsed:Float) {
|
||||
if(transitioning) {
|
||||
super.update(elapsed);
|
||||
return;
|
||||
}
|
||||
|
||||
if(character.animation.curAnim != null) {
|
||||
if(daText.finishedText) {
|
||||
if(character.animationIsLoop() && character.animation.curAnim.finished) {
|
||||
character.playAnim(character.animation.curAnim.name, true);
|
||||
}
|
||||
} else if(character.animation.curAnim.finished) {
|
||||
character.animation.curAnim.restart();
|
||||
}
|
||||
}
|
||||
|
||||
var blockInput:Bool = false;
|
||||
for (inputText in blockPressWhileTypingOn) {
|
||||
if(inputText.hasFocus) {
|
||||
FlxG.sound.muteKeys = [];
|
||||
FlxG.sound.volumeDownKeys = [];
|
||||
FlxG.sound.volumeUpKeys = [];
|
||||
blockInput = true;
|
||||
|
||||
if(FlxG.keys.pressed.CONTROL && FlxG.keys.justPressed.V && Clipboard.text != null) { //Copy paste
|
||||
inputText.text = ClipboardAdd(inputText.text);
|
||||
inputText.caretIndex = inputText.text.length;
|
||||
getEvent(FlxUIInputText.CHANGE_EVENT, inputText, null, []);
|
||||
}
|
||||
if(FlxG.keys.justPressed.ENTER) {
|
||||
if(inputText == lineInputText) {
|
||||
inputText.text += '\\n';
|
||||
inputText.caretIndex += 2;
|
||||
} else {
|
||||
inputText.hasFocus = false;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if(!blockInput) {
|
||||
FlxG.sound.muteKeys = TitleState.muteKeys;
|
||||
FlxG.sound.volumeDownKeys = TitleState.volumeDownKeys;
|
||||
FlxG.sound.volumeUpKeys = TitleState.volumeUpKeys;
|
||||
if(FlxG.keys.justPressed.SPACE) {
|
||||
reloadText(speedStepper.value);
|
||||
}
|
||||
if(FlxG.keys.justPressed.ESCAPE) {
|
||||
MusicBeatState.switchState(new editors.MasterEditorMenu());
|
||||
FlxG.sound.playMusic(Paths.music('freakyMenu'), 1);
|
||||
transitioning = true;
|
||||
}
|
||||
var negaMult:Array<Int> = [1, -1];
|
||||
var controlAnim:Array<Bool> = [FlxG.keys.justPressed.W, FlxG.keys.justPressed.S];
|
||||
var controlText:Array<Bool> = [FlxG.keys.justPressed.D, FlxG.keys.justPressed.A];
|
||||
for (i in 0...controlAnim.length) {
|
||||
if(controlAnim[i] && character.jsonFile.animations.length > 0) {
|
||||
curAnim += negaMult[i];
|
||||
if(curAnim < 0) curAnim = character.jsonFile.animations.length - 1;
|
||||
else if(curAnim >= character.jsonFile.animations.length) curAnim = 0;
|
||||
|
||||
var animToPlay:String = character.jsonFile.animations[curAnim].anim;
|
||||
if(character.dialogueAnimations.exists(animToPlay)) {
|
||||
character.playAnim(animToPlay, daText.finishedText);
|
||||
dialogueFile.dialogue[curSelected].expression = animToPlay;
|
||||
}
|
||||
animText.text = 'Animation: ' + animToPlay + ' (' + (curAnim + 1) +' / ' + character.jsonFile.animations.length + ') - Press W or S to scroll';
|
||||
}
|
||||
if(controlText[i]) {
|
||||
changeText(negaMult[i]);
|
||||
}
|
||||
}
|
||||
|
||||
if(FlxG.keys.justPressed.O) {
|
||||
dialogueFile.dialogue.remove(dialogueFile.dialogue[curSelected]);
|
||||
if(dialogueFile.dialogue.length < 1) //You deleted everything, dumbo!
|
||||
{
|
||||
dialogueFile.dialogue = [
|
||||
copyDefaultLine()
|
||||
];
|
||||
}
|
||||
changeText();
|
||||
} else if(FlxG.keys.justPressed.P) {
|
||||
dialogueFile.dialogue.insert(curSelected + 1, copyDefaultLine());
|
||||
changeText(1);
|
||||
}
|
||||
}
|
||||
super.update(elapsed);
|
||||
}
|
||||
|
||||
function changeText(add:Int = 0) {
|
||||
curSelected += add;
|
||||
if(curSelected < 0) curSelected = dialogueFile.dialogue.length - 1;
|
||||
else if(curSelected >= dialogueFile.dialogue.length) curSelected = 0;
|
||||
|
||||
var curDialogue:DialogueLine = dialogueFile.dialogue[curSelected];
|
||||
characterInputText.text = curDialogue.portrait;
|
||||
lineInputText.text = curDialogue.text;
|
||||
angryCheckbox.checked = (curDialogue.boxState == 'angry');
|
||||
speedStepper.value = curDialogue.speed;
|
||||
|
||||
curAnim = 0;
|
||||
character.reloadCharacterJson(characterInputText.text);
|
||||
reloadCharacter();
|
||||
updateTextBox();
|
||||
reloadText(curDialogue.speed);
|
||||
|
||||
var leLength:Int = character.jsonFile.animations.length;
|
||||
if(leLength > 0) {
|
||||
for (i in 0...leLength) {
|
||||
var leAnim:DialogueAnimArray = character.jsonFile.animations[i];
|
||||
if(leAnim != null && leAnim.anim == curDialogue.expression) {
|
||||
curAnim = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
character.playAnim(character.jsonFile.animations[curAnim].anim, daText.finishedText);
|
||||
animText.text = 'Animation: ' + character.jsonFile.animations[curAnim].anim + ' (' + (curAnim + 1) +' / ' + leLength + ') - Press W or S to scroll';
|
||||
} else {
|
||||
animText.text = 'ERROR! NO ANIMATIONS FOUND';
|
||||
}
|
||||
characterAnimSpeed();
|
||||
|
||||
selectedText.text = 'Line: (' + (curSelected + 1) + ' / ' + dialogueFile.dialogue.length + ') - Press A or D to scroll';
|
||||
}
|
||||
|
||||
function characterAnimSpeed() {
|
||||
if(character.animation.curAnim != null) {
|
||||
var speed:Float = speedStepper.value;
|
||||
var rate:Float = 24 - (((speed - 0.05) / 5) * 480);
|
||||
if(rate < 12) rate = 12;
|
||||
else if(rate > 48) rate = 48;
|
||||
character.animation.curAnim.frameRate = rate;
|
||||
}
|
||||
}
|
||||
|
||||
function ClipboardAdd(prefix:String = ''):String {
|
||||
if(prefix.toLowerCase().endsWith('v')) //probably copy paste attempt
|
||||
{
|
||||
prefix = prefix.substring(0, prefix.length-1);
|
||||
}
|
||||
|
||||
var text:String = prefix + Clipboard.text.replace('\n', '');
|
||||
return text;
|
||||
}
|
||||
|
||||
var _file:FileReference = null;
|
||||
function loadDialogue() {
|
||||
var jsonFilter:FileFilter = new FileFilter('JSON', 'json');
|
||||
_file = new FileReference();
|
||||
_file.addEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.addEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.addEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
_file.browse([jsonFilter]);
|
||||
}
|
||||
|
||||
function onLoadComplete(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
|
||||
#if sys
|
||||
var fullPath:String = null;
|
||||
var jsonLoaded = cast Json.parse(Json.stringify(_file)); //Exploit(???) for accessing a private variable
|
||||
if(jsonLoaded.__path != null) fullPath = jsonLoaded.__path; //I'm either a genious or dangerously dumb
|
||||
|
||||
if(fullPath != null) {
|
||||
var rawJson:String = File.getContent(fullPath);
|
||||
if(rawJson != null) {
|
||||
var loadedDialog:DialogueFile = cast Json.parse(rawJson);
|
||||
if(loadedDialog.dialogue != null && loadedDialog.dialogue.length > 0) //Make sure it's really a dialogue file
|
||||
{
|
||||
var cutName:String = _file.name.substr(0, _file.name.length - 5);
|
||||
trace("Successfully loaded file: " + cutName);
|
||||
dialogueFile = loadedDialog;
|
||||
changeText();
|
||||
_file = null;
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
_file = null;
|
||||
#else
|
||||
trace("File couldn't be loaded! You aren't on Desktop, are you?");
|
||||
#end
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the save file dialog is cancelled.
|
||||
*/
|
||||
function onLoadCancel(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
_file = null;
|
||||
trace("Cancelled file loading.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Called if there is an error while saving the gameplay recording.
|
||||
*/
|
||||
function onLoadError(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
_file = null;
|
||||
trace("Problem loading file");
|
||||
}
|
||||
|
||||
function saveDialogue() {
|
||||
var data:String = Json.stringify(dialogueFile, "\t");
|
||||
if (data.length > 0)
|
||||
{
|
||||
_file = new FileReference();
|
||||
_file.addEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.addEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.addEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file.save(data, "dialogue.json");
|
||||
}
|
||||
}
|
||||
|
||||
function onSaveComplete(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file = null;
|
||||
FlxG.log.notice("Successfully saved file.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the save file dialog is cancelled.
|
||||
*/
|
||||
function onSaveCancel(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file = null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Called if there is an error while saving the gameplay recording.
|
||||
*/
|
||||
function onSaveError(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file = null;
|
||||
FlxG.log.error("Problem saving file");
|
||||
}
|
||||
}
|
267
source/editors/EditorLua.hx
Normal file
267
source/editors/EditorLua.hx
Normal file
|
@ -0,0 +1,267 @@
|
|||
package editors;
|
||||
|
||||
#if LUA_ALLOWED
|
||||
import llua.Lua;
|
||||
import llua.LuaL;
|
||||
import llua.State;
|
||||
import llua.Convert;
|
||||
#end
|
||||
|
||||
import flixel.FlxG;
|
||||
import flixel.tweens.FlxTween;
|
||||
import flixel.tweens.FlxEase;
|
||||
import flixel.text.FlxText;
|
||||
import flixel.group.FlxGroup.FlxTypedGroup;
|
||||
import flixel.math.FlxPoint;
|
||||
import flixel.system.FlxSound;
|
||||
import flixel.util.FlxTimer;
|
||||
import flixel.FlxSprite;
|
||||
import flixel.FlxCamera;
|
||||
import flixel.util.FlxColor;
|
||||
import flixel.FlxBasic;
|
||||
#if sys
|
||||
import sys.FileSystem;
|
||||
import sys.io.File;
|
||||
#end
|
||||
import Type.ValueType;
|
||||
import Controls;
|
||||
import DialogueBoxPsych;
|
||||
|
||||
using StringTools;
|
||||
|
||||
class EditorLua {
|
||||
public static var Function_Stop = 1;
|
||||
public static var Function_Continue = 0;
|
||||
|
||||
#if LUA_ALLOWED
|
||||
public var lua:State = null;
|
||||
#end
|
||||
|
||||
var lePlayState:editors.EditorPlayState = null;
|
||||
|
||||
public function new(script:String) {
|
||||
#if LUA_ALLOWED
|
||||
lua = LuaL.newstate();
|
||||
LuaL.openlibs(lua);
|
||||
Lua.init_callbacks(lua);
|
||||
|
||||
//trace('Lua version: ' + Lua.version());
|
||||
//trace("LuaJIT version: " + Lua.versionJIT());
|
||||
|
||||
var result:Dynamic = LuaL.dofile(lua, script);
|
||||
var resultStr:String = Lua.tostring(lua, result);
|
||||
if(resultStr != null && result != 0) {
|
||||
lime.app.Application.current.window.alert(resultStr, 'Error on .LUA script!');
|
||||
trace('Error on .LUA script! ' + resultStr);
|
||||
lua = null;
|
||||
return;
|
||||
}
|
||||
trace('Lua file loaded succesfully:' + script);
|
||||
|
||||
var curState:Dynamic = FlxG.state;
|
||||
lePlayState = curState;
|
||||
|
||||
// Lua variables
|
||||
set('Function_Stop', Function_Stop);
|
||||
set('Function_Continue', Function_Continue);
|
||||
set('inChartEditor', true);
|
||||
|
||||
set('curBpm', Conductor.bpm);
|
||||
set('bpm', PlayState.SONG.bpm);
|
||||
set('scrollSpeed', PlayState.SONG.speed);
|
||||
set('crochet', Conductor.crochet);
|
||||
set('stepCrochet', Conductor.stepCrochet);
|
||||
set('songLength', FlxG.sound.music.length);
|
||||
set('songName', PlayState.SONG.song);
|
||||
|
||||
set('screenWidth', FlxG.width);
|
||||
set('screenHeight', FlxG.height);
|
||||
|
||||
for (i in 0...4) {
|
||||
set('defaultPlayerStrumX' + i, 0);
|
||||
set('defaultPlayerStrumY' + i, 0);
|
||||
set('defaultOpponentStrumX' + i, 0);
|
||||
set('defaultOpponentStrumY' + i, 0);
|
||||
}
|
||||
|
||||
set('downscroll', ClientPrefs.downScroll);
|
||||
set('middlescroll', ClientPrefs.middleScroll);
|
||||
|
||||
//stuff 4 noobz like you B)
|
||||
Lua_helper.add_callback(lua, "getProperty", function(variable:String) {
|
||||
var killMe:Array<String> = variable.split('.');
|
||||
if(killMe.length > 1) {
|
||||
var coverMeInPiss:Dynamic = Reflect.getProperty(lePlayState, killMe[0]);
|
||||
|
||||
for (i in 1...killMe.length-1) {
|
||||
coverMeInPiss = Reflect.getProperty(coverMeInPiss, killMe[i]);
|
||||
}
|
||||
return Reflect.getProperty(coverMeInPiss, killMe[killMe.length-1]);
|
||||
}
|
||||
return Reflect.getProperty(lePlayState, variable);
|
||||
});
|
||||
Lua_helper.add_callback(lua, "setProperty", function(variable:String, value:Dynamic) {
|
||||
var killMe:Array<String> = variable.split('.');
|
||||
if(killMe.length > 1) {
|
||||
var coverMeInPiss:Dynamic = Reflect.getProperty(lePlayState, killMe[0]);
|
||||
|
||||
for (i in 1...killMe.length-1) {
|
||||
coverMeInPiss = Reflect.getProperty(coverMeInPiss, killMe[i]);
|
||||
}
|
||||
return Reflect.setProperty(coverMeInPiss, killMe[killMe.length-1], value);
|
||||
}
|
||||
return Reflect.setProperty(lePlayState, variable, value);
|
||||
});
|
||||
Lua_helper.add_callback(lua, "getPropertyFromGroup", function(obj:String, index:Int, variable:Dynamic) {
|
||||
if(Std.isOfType(Reflect.getProperty(lePlayState, obj), FlxTypedGroup)) {
|
||||
return Reflect.getProperty(Reflect.getProperty(lePlayState, obj).members[index], variable);
|
||||
}
|
||||
|
||||
var leArray:Dynamic = Reflect.getProperty(lePlayState, obj)[index];
|
||||
if(leArray != null) {
|
||||
if(Type.typeof(variable) == ValueType.TInt) {
|
||||
return leArray[variable];
|
||||
}
|
||||
return Reflect.getProperty(leArray, variable);
|
||||
}
|
||||
return null;
|
||||
});
|
||||
Lua_helper.add_callback(lua, "setPropertyFromGroup", function(obj:String, index:Int, variable:Dynamic, value:Dynamic) {
|
||||
if(Std.isOfType(Reflect.getProperty(lePlayState, obj), FlxTypedGroup)) {
|
||||
return Reflect.setProperty(Reflect.getProperty(lePlayState, obj).members[index], variable, value);
|
||||
}
|
||||
|
||||
var leArray:Dynamic = Reflect.getProperty(lePlayState, obj)[index];
|
||||
if(leArray != null) {
|
||||
if(Type.typeof(variable) == ValueType.TInt) {
|
||||
return leArray[variable] = value;
|
||||
}
|
||||
return Reflect.setProperty(leArray, variable, value);
|
||||
}
|
||||
});
|
||||
Lua_helper.add_callback(lua, "removeFromGroup", function(obj:String, index:Int, dontDestroy:Bool = false) {
|
||||
if(Std.isOfType(Reflect.getProperty(lePlayState, obj), FlxTypedGroup)) {
|
||||
var sex = Reflect.getProperty(lePlayState, obj).members[index];
|
||||
if(!dontDestroy)
|
||||
sex.kill();
|
||||
Reflect.getProperty(lePlayState, obj).remove(sex, true);
|
||||
if(!dontDestroy)
|
||||
sex.destroy();
|
||||
return;
|
||||
}
|
||||
Reflect.getProperty(lePlayState, obj).remove(Reflect.getProperty(lePlayState, obj)[index]);
|
||||
});
|
||||
|
||||
Lua_helper.add_callback(lua, "getColorFromHex", function(color:String) {
|
||||
if(!color.startsWith('0x')) color = '0xff' + color;
|
||||
return Std.parseInt(color);
|
||||
});
|
||||
|
||||
Lua_helper.add_callback(lua, "setGraphicSize", function(obj:String, x:Int, y:Int = 0) {
|
||||
var poop:FlxSprite = Reflect.getProperty(lePlayState, obj);
|
||||
if(poop != null) {
|
||||
poop.setGraphicSize(x, y);
|
||||
poop.updateHitbox();
|
||||
return;
|
||||
}
|
||||
});
|
||||
Lua_helper.add_callback(lua, "scaleObject", function(obj:String, x:Float, y:Float) {
|
||||
var poop:FlxSprite = Reflect.getProperty(lePlayState, obj);
|
||||
if(poop != null) {
|
||||
poop.scale.set(x, y);
|
||||
poop.updateHitbox();
|
||||
return;
|
||||
}
|
||||
});
|
||||
Lua_helper.add_callback(lua, "updateHitbox", function(obj:String) {
|
||||
var poop:FlxSprite = Reflect.getProperty(lePlayState, obj);
|
||||
if(poop != null) {
|
||||
poop.updateHitbox();
|
||||
return;
|
||||
}
|
||||
});
|
||||
call('onCreate', []);
|
||||
#end
|
||||
}
|
||||
|
||||
public function call(event:String, args:Array<Dynamic>):Dynamic {
|
||||
#if LUA_ALLOWED
|
||||
if(lua == null) {
|
||||
return Function_Continue;
|
||||
}
|
||||
|
||||
Lua.getglobal(lua, event);
|
||||
|
||||
for (arg in args) {
|
||||
Convert.toLua(lua, arg);
|
||||
}
|
||||
|
||||
var result:Null<Int> = Lua.pcall(lua, args.length, 1, 0);
|
||||
if(result != null && resultIsAllowed(lua, result)) {
|
||||
/*var resultStr:String = Lua.tostring(lua, result);
|
||||
var error:String = Lua.tostring(lua, -1);
|
||||
Lua.pop(lua, 1);*/
|
||||
if(Lua.type(lua, -1) == Lua.LUA_TSTRING) {
|
||||
var error:String = Lua.tostring(lua, -1);
|
||||
Lua.pop(lua, 1);
|
||||
if(error == 'attempt to call a nil value') { //Makes it ignore warnings and not break stuff if you didn't put the functions on your lua file
|
||||
return Function_Continue;
|
||||
}
|
||||
}
|
||||
|
||||
var conv:Dynamic = Convert.fromLua(lua, result);
|
||||
return conv;
|
||||
}
|
||||
#end
|
||||
return Function_Continue;
|
||||
}
|
||||
|
||||
#if LUA_ALLOWED
|
||||
function resultIsAllowed(leLua:State, leResult:Null<Int>) { //Makes it ignore warnings
|
||||
switch(Lua.type(leLua, leResult)) {
|
||||
case Lua.LUA_TNIL | Lua.LUA_TBOOLEAN | Lua.LUA_TNUMBER | Lua.LUA_TSTRING | Lua.LUA_TTABLE:
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
#end
|
||||
|
||||
public function set(variable:String, data:Dynamic) {
|
||||
#if LUA_ALLOWED
|
||||
if(lua == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
Convert.toLua(lua, data);
|
||||
Lua.setglobal(lua, variable);
|
||||
#end
|
||||
}
|
||||
|
||||
#if LUA_ALLOWED
|
||||
public function getBool(variable:String) {
|
||||
var result:String = null;
|
||||
Lua.getglobal(lua, variable);
|
||||
result = Convert.fromLua(lua, -1);
|
||||
Lua.pop(lua, 1);
|
||||
|
||||
if(result == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// YES! FINALLY IT WORKS
|
||||
//trace('variable: ' + variable + ', ' + result);
|
||||
return (result == 'true');
|
||||
}
|
||||
#end
|
||||
|
||||
public function stop() {
|
||||
#if LUA_ALLOWED
|
||||
if(lua == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
Lua.close(lua);
|
||||
lua = null;
|
||||
#end
|
||||
}
|
||||
}
|
878
source/editors/EditorPlayState.hx
Normal file
878
source/editors/EditorPlayState.hx
Normal file
|
@ -0,0 +1,878 @@
|
|||
package editors;
|
||||
|
||||
import Section.SwagSection;
|
||||
import Song.SwagSong;
|
||||
import flixel.group.FlxGroup.FlxTypedGroup;
|
||||
import flixel.addons.transition.FlxTransitionableState;
|
||||
import flixel.util.FlxColor;
|
||||
import flixel.FlxSprite;
|
||||
import flixel.FlxG;
|
||||
import flixel.text.FlxText;
|
||||
import flixel.tweens.FlxEase;
|
||||
import flixel.tweens.FlxTween;
|
||||
import flixel.math.FlxMath;
|
||||
import flixel.math.FlxPoint;
|
||||
import flixel.math.FlxRect;
|
||||
import flixel.system.FlxSound;
|
||||
import flixel.util.FlxSort;
|
||||
import flixel.util.FlxTimer;
|
||||
import FunkinLua;
|
||||
|
||||
using StringTools;
|
||||
|
||||
class EditorPlayState extends MusicBeatState
|
||||
{
|
||||
// Yes, this is mostly a copy of PlayState, it's kinda dumb to make a direct copy of it but... ehhh
|
||||
private var strumLine:FlxSprite;
|
||||
private var comboGroup:FlxTypedGroup<FlxSprite>;
|
||||
public var strumLineNotes:FlxTypedGroup<StrumNote>;
|
||||
public var opponentStrums:FlxTypedGroup<StrumNote>;
|
||||
public var playerStrums:FlxTypedGroup<StrumNote>;
|
||||
public var grpNoteSplashes:FlxTypedGroup<NoteSplash>;
|
||||
|
||||
public var notes:FlxTypedGroup<Note>;
|
||||
public var unspawnNotes:Array<Note> = [];
|
||||
|
||||
var generatedMusic:Bool = false;
|
||||
var vocals:FlxSound;
|
||||
|
||||
var startOffset:Float = 0;
|
||||
var startPos:Float = 0;
|
||||
|
||||
public function new(startPos:Float) {
|
||||
this.startPos = startPos;
|
||||
Conductor.songPosition = startPos - startOffset;
|
||||
|
||||
startOffset = Conductor.crochet;
|
||||
timerToStart = startOffset;
|
||||
super();
|
||||
}
|
||||
|
||||
var scoreTxt:FlxText;
|
||||
var timerToStart:Float = 0;
|
||||
private var noteTypeMap:Map<String, Bool> = new Map<String, Bool>();
|
||||
override function create()
|
||||
{
|
||||
var bg:FlxSprite = new FlxSprite().loadGraphic(Paths.image('menuDesat'));
|
||||
bg.scrollFactor.set();
|
||||
bg.color = FlxColor.fromHSB(FlxG.random.int(0, 359), FlxG.random.float(0, 0.8), FlxG.random.float(0.3, 1));
|
||||
add(bg);
|
||||
|
||||
strumLine = new FlxSprite(ClientPrefs.middleScroll ? PlayState.STRUM_X_MIDDLESCROLL : PlayState.STRUM_X, 50).makeGraphic(FlxG.width, 10);
|
||||
if(ClientPrefs.downScroll) strumLine.y = FlxG.height - 150;
|
||||
strumLine.scrollFactor.set();
|
||||
|
||||
comboGroup = new FlxTypedGroup<FlxSprite>();
|
||||
add(comboGroup);
|
||||
|
||||
strumLineNotes = new FlxTypedGroup<StrumNote>();
|
||||
opponentStrums = new FlxTypedGroup<StrumNote>();
|
||||
playerStrums = new FlxTypedGroup<StrumNote>();
|
||||
add(strumLineNotes);
|
||||
|
||||
generateStaticArrows(0);
|
||||
generateStaticArrows(1);
|
||||
if(ClientPrefs.middleScroll) {
|
||||
opponentStrums.forEachAlive(function (note:StrumNote) {
|
||||
note.visible = false;
|
||||
});
|
||||
}
|
||||
|
||||
grpNoteSplashes = new FlxTypedGroup<NoteSplash>();
|
||||
add(grpNoteSplashes);
|
||||
|
||||
var splash:NoteSplash = new NoteSplash(100, 100, 0);
|
||||
grpNoteSplashes.add(splash);
|
||||
splash.alpha = 0.0;
|
||||
|
||||
if (PlayState.SONG.needsVoices)
|
||||
vocals = new FlxSound().loadEmbedded(Paths.voices(PlayState.SONG.song));
|
||||
else
|
||||
vocals = new FlxSound();
|
||||
|
||||
generateSong(PlayState.SONG.song);
|
||||
#if LUA_ALLOWED
|
||||
for (notetype in noteTypeMap.keys()) {
|
||||
var luaToLoad:String = Paths.modFolders('custom_notetypes/' + notetype + '.lua');
|
||||
if(sys.FileSystem.exists(luaToLoad)) {
|
||||
var lua:editors.EditorLua = new editors.EditorLua(luaToLoad);
|
||||
new FlxTimer().start(0.1, function (tmr:FlxTimer) {
|
||||
lua.stop();
|
||||
lua = null;
|
||||
});
|
||||
}
|
||||
}
|
||||
#end
|
||||
noteTypeMap.clear();
|
||||
noteTypeMap = null;
|
||||
|
||||
scoreTxt = new FlxText(0, FlxG.height - 50, FlxG.width, "Hits: 0 | Misses: 0", 20);
|
||||
scoreTxt.setFormat(Paths.font("vcr.ttf"), 20, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK);
|
||||
scoreTxt.scrollFactor.set();
|
||||
scoreTxt.borderSize = 1.25;
|
||||
scoreTxt.visible = !ClientPrefs.hideHud;
|
||||
add(scoreTxt);
|
||||
|
||||
var tipText:FlxText = new FlxText(10, FlxG.height - 24, 0, 'Press ESC to Go Back to Chart Editor', 16);
|
||||
tipText.setFormat(Paths.font("vcr.ttf"), 16, FlxColor.WHITE, LEFT, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK);
|
||||
tipText.borderSize = 2;
|
||||
tipText.scrollFactor.set();
|
||||
add(tipText);
|
||||
FlxG.mouse.visible = false;
|
||||
|
||||
//sayGo();
|
||||
super.create();
|
||||
}
|
||||
|
||||
function sayGo() {
|
||||
var go:FlxSprite = new FlxSprite().loadGraphic(Paths.image('go'));
|
||||
go.scrollFactor.set();
|
||||
|
||||
go.updateHitbox();
|
||||
|
||||
go.screenCenter();
|
||||
go.antialiasing = ClientPrefs.globalAntialiasing;
|
||||
add(go);
|
||||
FlxTween.tween(go, {y: go.y += 100, alpha: 0}, Conductor.crochet / 1000, {
|
||||
ease: FlxEase.cubeInOut,
|
||||
onComplete: function(twn:FlxTween)
|
||||
{
|
||||
go.destroy();
|
||||
}
|
||||
});
|
||||
FlxG.sound.play(Paths.sound('introGo'), 0.6);
|
||||
}
|
||||
|
||||
//var songScore:Int = 0;
|
||||
var songHits:Int = 0;
|
||||
var songMisses:Int = 0;
|
||||
var ghostMisses:Int = 0;
|
||||
var startingSong:Bool = true;
|
||||
private function generateSong(dataPath:String):Void
|
||||
{
|
||||
FlxG.sound.playMusic(Paths.inst(PlayState.SONG.song), 0, false);
|
||||
FlxG.sound.music.pause();
|
||||
FlxG.sound.music.onComplete = endSong;
|
||||
vocals.pause();
|
||||
vocals.volume = 0;
|
||||
|
||||
var songData = PlayState.SONG;
|
||||
Conductor.changeBPM(songData.bpm);
|
||||
|
||||
notes = new FlxTypedGroup<Note>();
|
||||
add(notes);
|
||||
|
||||
var noteData:Array<SwagSection>;
|
||||
|
||||
// NEW SHIT
|
||||
noteData = songData.notes;
|
||||
|
||||
var playerCounter:Int = 0;
|
||||
|
||||
var daBeats:Int = 0; // Not exactly representative of 'daBeats' lol, just how much it has looped
|
||||
|
||||
for (section in noteData)
|
||||
{
|
||||
for (songNotes in section.sectionNotes)
|
||||
{
|
||||
if(songNotes[1] > -1) { //Real notes
|
||||
var daStrumTime:Float = songNotes[0];
|
||||
if(daStrumTime >= startPos) {
|
||||
var daNoteData:Int = Std.int(songNotes[1] % 4);
|
||||
|
||||
var gottaHitNote:Bool = section.mustHitSection;
|
||||
|
||||
if (songNotes[1] > 3)
|
||||
{
|
||||
gottaHitNote = !section.mustHitSection;
|
||||
}
|
||||
|
||||
var oldNote:Note;
|
||||
if (unspawnNotes.length > 0)
|
||||
oldNote = unspawnNotes[Std.int(unspawnNotes.length - 1)];
|
||||
else
|
||||
oldNote = null;
|
||||
|
||||
var swagNote:Note = new Note(daStrumTime, daNoteData, oldNote);
|
||||
swagNote.mustPress = gottaHitNote;
|
||||
swagNote.sustainLength = songNotes[2];
|
||||
swagNote.noteType = songNotes[3];
|
||||
if(!Std.isOfType(songNotes[3], String)) swagNote.noteType = editors.ChartingState.noteTypeList[songNotes[3]]; //Backward compatibility + compatibility with Week 7 charts
|
||||
swagNote.scrollFactor.set();
|
||||
|
||||
var susLength:Float = swagNote.sustainLength;
|
||||
|
||||
susLength = susLength / Conductor.stepCrochet;
|
||||
unspawnNotes.push(swagNote);
|
||||
|
||||
var floorSus:Int = Math.floor(susLength);
|
||||
if(floorSus > 0) {
|
||||
for (susNote in 0...floorSus+1)
|
||||
{
|
||||
oldNote = unspawnNotes[Std.int(unspawnNotes.length - 1)];
|
||||
|
||||
var sustainNote:Note = new Note(daStrumTime + (Conductor.stepCrochet * susNote) + (Conductor.stepCrochet / FlxMath.roundDecimal(PlayState.SONG.speed, 2)), daNoteData, oldNote, true);
|
||||
sustainNote.mustPress = gottaHitNote;
|
||||
sustainNote.noteType = swagNote.noteType;
|
||||
sustainNote.scrollFactor.set();
|
||||
unspawnNotes.push(sustainNote);
|
||||
|
||||
if (sustainNote.mustPress)
|
||||
{
|
||||
sustainNote.x += FlxG.width / 2; // general offset
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (swagNote.mustPress)
|
||||
{
|
||||
swagNote.x += FlxG.width / 2; // general offset
|
||||
}
|
||||
else {}
|
||||
|
||||
if(!noteTypeMap.exists(swagNote.noteType)) {
|
||||
noteTypeMap.set(swagNote.noteType, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
daBeats += 1;
|
||||
}
|
||||
|
||||
unspawnNotes.sort(sortByShit);
|
||||
generatedMusic = true;
|
||||
}
|
||||
|
||||
function startSong():Void
|
||||
{
|
||||
startingSong = false;
|
||||
FlxG.sound.music.time = startPos;
|
||||
FlxG.sound.music.play();
|
||||
FlxG.sound.music.volume = 1;
|
||||
vocals.volume = 1;
|
||||
vocals.time = startPos;
|
||||
vocals.play();
|
||||
}
|
||||
|
||||
function sortByShit(Obj1:Note, Obj2:Note):Int
|
||||
{
|
||||
return FlxSort.byValues(FlxSort.ASCENDING, Obj1.strumTime, Obj2.strumTime);
|
||||
}
|
||||
|
||||
private function endSong() {
|
||||
LoadingState.loadAndSwitchState(new editors.ChartingState());
|
||||
}
|
||||
|
||||
override function update(elapsed:Float) {
|
||||
if (FlxG.keys.justPressed.ESCAPE)
|
||||
{
|
||||
FlxG.sound.music.pause();
|
||||
vocals.pause();
|
||||
LoadingState.loadAndSwitchState(new editors.ChartingState());
|
||||
}
|
||||
|
||||
if (startingSong) {
|
||||
timerToStart -= elapsed * 1000;
|
||||
Conductor.songPosition = startPos - timerToStart;
|
||||
if(timerToStart < 0) {
|
||||
startSong();
|
||||
}
|
||||
} else {
|
||||
Conductor.songPosition += elapsed * 1000;
|
||||
}
|
||||
|
||||
var roundedSpeed:Float = FlxMath.roundDecimal(PlayState.SONG.speed, 2);
|
||||
if (unspawnNotes[0] != null)
|
||||
{
|
||||
var time:Float = 1500;
|
||||
if(roundedSpeed < 1) time /= roundedSpeed;
|
||||
|
||||
while (unspawnNotes.length > 0 && unspawnNotes[0].strumTime - Conductor.songPosition < time)
|
||||
{
|
||||
var dunceNote:Note = unspawnNotes[0];
|
||||
notes.add(dunceNote);
|
||||
|
||||
var index:Int = unspawnNotes.indexOf(dunceNote);
|
||||
unspawnNotes.splice(index, 1);
|
||||
}
|
||||
}
|
||||
|
||||
if (generatedMusic)
|
||||
{
|
||||
var fakeCrochet:Float = (60 / PlayState.SONG.bpm) * 1000;
|
||||
notes.forEachAlive(function(daNote:Note)
|
||||
{
|
||||
if(!daNote.mustPress && ClientPrefs.middleScroll)
|
||||
{
|
||||
daNote.active = true;
|
||||
daNote.visible = false;
|
||||
}
|
||||
else if (daNote.y > FlxG.height)
|
||||
{
|
||||
daNote.active = false;
|
||||
daNote.visible = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
daNote.visible = true;
|
||||
daNote.active = true;
|
||||
}
|
||||
|
||||
// i am so fucking sorry for this if condition
|
||||
var strumX:Float = 0;
|
||||
var strumY:Float = 0;
|
||||
if(daNote.mustPress) {
|
||||
strumX = playerStrums.members[daNote.noteData].x;
|
||||
strumY = playerStrums.members[daNote.noteData].y;
|
||||
} else {
|
||||
strumX = opponentStrums.members[daNote.noteData].x;
|
||||
strumY = opponentStrums.members[daNote.noteData].y;
|
||||
}
|
||||
|
||||
strumX += daNote.offsetX;
|
||||
strumY += daNote.offsetY;
|
||||
var center:Float = strumY + Note.swagWidth / 2;
|
||||
|
||||
if(daNote.copyX) {
|
||||
daNote.x = strumX;
|
||||
}
|
||||
if(daNote.copyY) {
|
||||
if (ClientPrefs.downScroll) {
|
||||
daNote.y = (strumY + 0.45 * (Conductor.songPosition - daNote.strumTime) * roundedSpeed);
|
||||
if (daNote.isSustainNote) {
|
||||
//Jesus fuck this took me so much mother fucking time AAAAAAAAAA
|
||||
if (daNote.animation.curAnim.name.endsWith('end')) {
|
||||
daNote.y += 10.5 * (fakeCrochet / 400) * 1.5 * roundedSpeed + (46 * (roundedSpeed - 1));
|
||||
daNote.y -= 46 * (1 - (fakeCrochet / 600)) * roundedSpeed;
|
||||
if(PlayState.isPixelStage) {
|
||||
daNote.y += 8;
|
||||
} else {
|
||||
daNote.y -= 19;
|
||||
}
|
||||
}
|
||||
daNote.y += (Note.swagWidth / 2) - (60.5 * (roundedSpeed - 1));
|
||||
daNote.y += 27.5 * ((PlayState.SONG.bpm / 100) - 1) * (roundedSpeed - 1);
|
||||
|
||||
if(daNote.mustPress || !daNote.ignoreNote)
|
||||
{
|
||||
if(daNote.y - daNote.offset.y * daNote.scale.y + daNote.height >= center
|
||||
&& (!daNote.mustPress || (daNote.wasGoodHit || (daNote.prevNote.wasGoodHit && !daNote.canBeHit))))
|
||||
{
|
||||
var swagRect = new FlxRect(0, 0, daNote.frameWidth, daNote.frameHeight);
|
||||
swagRect.height = (center - daNote.y) / daNote.scale.y;
|
||||
swagRect.y = daNote.frameHeight - swagRect.height;
|
||||
|
||||
daNote.clipRect = swagRect;
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
daNote.y = (strumY - 0.45 * (Conductor.songPosition - daNote.strumTime) * roundedSpeed);
|
||||
|
||||
if(daNote.mustPress || !daNote.ignoreNote)
|
||||
{
|
||||
if (daNote.isSustainNote
|
||||
&& daNote.y + daNote.offset.y * daNote.scale.y <= center
|
||||
&& (!daNote.mustPress || (daNote.wasGoodHit || (daNote.prevNote.wasGoodHit && !daNote.canBeHit))))
|
||||
{
|
||||
var swagRect = new FlxRect(0, 0, daNote.width / daNote.scale.x, daNote.height / daNote.scale.y);
|
||||
swagRect.y = (center - daNote.y) / daNote.scale.y;
|
||||
swagRect.height -= swagRect.y;
|
||||
|
||||
daNote.clipRect = swagRect;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!daNote.mustPress && daNote.wasGoodHit && !daNote.hitByOpponent && !daNote.ignoreNote)
|
||||
{
|
||||
if (PlayState.SONG.needsVoices)
|
||||
vocals.volume = 1;
|
||||
|
||||
var time:Float = 0.15;
|
||||
if(daNote.isSustainNote && !daNote.animation.curAnim.name.endsWith('end')) {
|
||||
time += 0.15;
|
||||
}
|
||||
StrumPlayAnim(true, Std.int(Math.abs(daNote.noteData)) % 4, time);
|
||||
daNote.hitByOpponent = true;
|
||||
|
||||
if (!daNote.isSustainNote)
|
||||
{
|
||||
daNote.kill();
|
||||
notes.remove(daNote, true);
|
||||
daNote.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
var doKill:Bool = daNote.y < -daNote.height;
|
||||
if(ClientPrefs.downScroll) doKill = daNote.y > FlxG.height;
|
||||
|
||||
if (doKill)
|
||||
{
|
||||
if (daNote.mustPress)
|
||||
{
|
||||
if (daNote.tooLate || !daNote.wasGoodHit)
|
||||
{
|
||||
//Dupe note remove
|
||||
notes.forEachAlive(function(note:Note) {
|
||||
if (daNote != note && daNote.mustPress && daNote.noteData == note.noteData && daNote.isSustainNote == note.isSustainNote && Math.abs(daNote.strumTime - note.strumTime) < 10) {
|
||||
note.kill();
|
||||
notes.remove(note, true);
|
||||
note.destroy();
|
||||
}
|
||||
});
|
||||
|
||||
if(!daNote.ignoreNote) {
|
||||
songMisses++;
|
||||
vocals.volume = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
daNote.active = false;
|
||||
daNote.visible = false;
|
||||
|
||||
daNote.kill();
|
||||
notes.remove(daNote, true);
|
||||
daNote.destroy();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
keyShit();
|
||||
scoreTxt.text = 'Hits: ' + songHits + ' | Misses: ' + songMisses;
|
||||
super.update(elapsed);
|
||||
}
|
||||
|
||||
override function beatHit()
|
||||
{
|
||||
super.beatHit();
|
||||
|
||||
if (generatedMusic)
|
||||
{
|
||||
notes.sort(FlxSort.byY, ClientPrefs.downScroll ? FlxSort.ASCENDING : FlxSort.DESCENDING);
|
||||
}
|
||||
}
|
||||
|
||||
override function stepHit()
|
||||
{
|
||||
super.stepHit();
|
||||
if (FlxG.sound.music.time > Conductor.songPosition + 20 || FlxG.sound.music.time < Conductor.songPosition - 20)
|
||||
{
|
||||
resyncVocals();
|
||||
}
|
||||
}
|
||||
|
||||
function resyncVocals():Void
|
||||
{
|
||||
vocals.pause();
|
||||
|
||||
FlxG.sound.music.play();
|
||||
Conductor.songPosition = FlxG.sound.music.time;
|
||||
vocals.time = Conductor.songPosition;
|
||||
vocals.play();
|
||||
}
|
||||
|
||||
function keyShit() {
|
||||
// HOLDING
|
||||
var up = controls.NOTE_UP;
|
||||
var right = controls.NOTE_RIGHT;
|
||||
var down = controls.NOTE_DOWN;
|
||||
var left = controls.NOTE_LEFT;
|
||||
|
||||
var upP = controls.NOTE_UP_P;
|
||||
var rightP = controls.NOTE_RIGHT_P;
|
||||
var downP = controls.NOTE_DOWN_P;
|
||||
var leftP = controls.NOTE_LEFT_P;
|
||||
|
||||
var upR = controls.NOTE_UP_R;
|
||||
var rightR = controls.NOTE_RIGHT_R;
|
||||
var downR = controls.NOTE_DOWN_R;
|
||||
var leftR = controls.NOTE_LEFT_R;
|
||||
|
||||
var controlArray:Array<Bool> = [leftP, downP, upP, rightP];
|
||||
var controlReleaseArray:Array<Bool> = [leftR, downR, upR, rightR];
|
||||
var controlHoldArray:Array<Bool> = [left, down, up, right];
|
||||
|
||||
// FlxG.watch.addQuick('asdfa', upP);
|
||||
if (generatedMusic)
|
||||
{
|
||||
// rewritten inputs???
|
||||
notes.forEachAlive(function(daNote:Note)
|
||||
{
|
||||
// hold note functions
|
||||
if (daNote.isSustainNote && controlHoldArray[daNote.noteData] && daNote.canBeHit
|
||||
&& daNote.mustPress && !daNote.tooLate && !daNote.wasGoodHit) {
|
||||
goodNoteHit(daNote);
|
||||
}
|
||||
});
|
||||
|
||||
if (controlHoldArray.contains(true) || controlArray.contains(true)) {
|
||||
var canMiss:Bool = !ClientPrefs.ghostTapping;
|
||||
if (controlArray.contains(true)) {
|
||||
for (i in 0...controlArray.length) {
|
||||
// heavily based on my own code LOL if it aint broke dont fix it
|
||||
var pressNotes:Array<Note> = [];
|
||||
var notesDatas:Array<Int> = [];
|
||||
var notesStopped:Bool = false;
|
||||
|
||||
var sortedNotesList:Array<Note> = [];
|
||||
notes.forEachAlive(function(daNote:Note)
|
||||
{
|
||||
if (daNote.canBeHit && daNote.mustPress && !daNote.tooLate
|
||||
&& !daNote.wasGoodHit && daNote.noteData == i) {
|
||||
sortedNotesList.push(daNote);
|
||||
notesDatas.push(daNote.noteData);
|
||||
canMiss = true;
|
||||
}
|
||||
});
|
||||
sortedNotesList.sort((a, b) -> Std.int(a.strumTime - b.strumTime));
|
||||
|
||||
if (sortedNotesList.length > 0) {
|
||||
for (epicNote in sortedNotesList)
|
||||
{
|
||||
for (doubleNote in pressNotes) {
|
||||
if (Math.abs(doubleNote.strumTime - epicNote.strumTime) < 10) {
|
||||
doubleNote.kill();
|
||||
notes.remove(doubleNote, true);
|
||||
doubleNote.destroy();
|
||||
} else
|
||||
notesStopped = true;
|
||||
}
|
||||
|
||||
// eee jack detection before was not super good
|
||||
if (controlArray[epicNote.noteData] && !notesStopped) {
|
||||
goodNoteHit(epicNote);
|
||||
pressNotes.push(epicNote);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
else if (canMiss && controlArray[i])
|
||||
noteMiss(i, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
playerStrums.forEach(function(spr:StrumNote)
|
||||
{
|
||||
if(controlArray[spr.ID] && spr.animation.curAnim.name != 'confirm') {
|
||||
spr.playAnim('pressed');
|
||||
spr.resetAnim = 0;
|
||||
}
|
||||
if(controlReleaseArray[spr.ID]) {
|
||||
spr.playAnim('static');
|
||||
spr.resetAnim = 0;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
var combo:Int = 0;
|
||||
function goodNoteHit(note:Note):Void
|
||||
{
|
||||
if (!note.wasGoodHit)
|
||||
{
|
||||
switch(note.noteType) {
|
||||
case 'Hurt Note': //Hurt note
|
||||
noteMiss(note.noteData);
|
||||
--songMisses;
|
||||
if(!note.isSustainNote) {
|
||||
if(!note.noteSplashDisabled) {
|
||||
spawnNoteSplashOnNote(note);
|
||||
}
|
||||
}
|
||||
|
||||
note.wasGoodHit = true;
|
||||
vocals.volume = 0;
|
||||
|
||||
if (!note.isSustainNote)
|
||||
{
|
||||
note.kill();
|
||||
notes.remove(note, true);
|
||||
note.destroy();
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (!note.isSustainNote)
|
||||
{
|
||||
popUpScore(note);
|
||||
combo += 1;
|
||||
songHits++;
|
||||
if(combo > 9999) combo = 9999;
|
||||
}
|
||||
|
||||
playerStrums.forEach(function(spr:StrumNote)
|
||||
{
|
||||
if (Math.abs(note.noteData) == spr.ID)
|
||||
{
|
||||
spr.playAnim('confirm', true);
|
||||
}
|
||||
});
|
||||
|
||||
note.wasGoodHit = true;
|
||||
vocals.volume = 1;
|
||||
|
||||
if (!note.isSustainNote)
|
||||
{
|
||||
note.kill();
|
||||
notes.remove(note, true);
|
||||
note.destroy();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function noteMiss(direction:Int = 1, ?ghostMiss:Bool = false):Void
|
||||
{
|
||||
combo = 0;
|
||||
|
||||
//songScore -= 10;
|
||||
if(ghostMiss) ghostMisses++;
|
||||
songMisses++;
|
||||
|
||||
FlxG.sound.play(Paths.soundRandom('missnote', 1, 3), FlxG.random.float(0.1, 0.2));
|
||||
vocals.volume = 0;
|
||||
}
|
||||
|
||||
var COMBO_X:Float = 400;
|
||||
var COMBO_Y:Float = 340;
|
||||
private function popUpScore(note:Note = null):Void
|
||||
{
|
||||
var noteDiff:Float = Math.abs(note.strumTime - Conductor.songPosition + 8);
|
||||
|
||||
vocals.volume = 1;
|
||||
|
||||
var placement:String = Std.string(combo);
|
||||
|
||||
var coolText:FlxText = new FlxText(0, 0, 0, placement, 32);
|
||||
coolText.x = COMBO_X;
|
||||
coolText.y = COMBO_Y;
|
||||
//
|
||||
|
||||
var rating:FlxSprite = new FlxSprite();
|
||||
//var score:Int = 350;
|
||||
|
||||
var daRating:String = "sick";
|
||||
|
||||
if (noteDiff > Conductor.safeZoneOffset * 0.75)
|
||||
{
|
||||
daRating = 'shit';
|
||||
//score = 50;
|
||||
}
|
||||
else if (noteDiff > Conductor.safeZoneOffset * 0.5)
|
||||
{
|
||||
daRating = 'bad';
|
||||
//score = 100;
|
||||
}
|
||||
else if (noteDiff > Conductor.safeZoneOffset * 0.25)
|
||||
{
|
||||
daRating = 'good';
|
||||
//score = 200;
|
||||
}
|
||||
|
||||
if(daRating == 'sick' && !note.noteSplashDisabled)
|
||||
{
|
||||
spawnNoteSplashOnNote(note);
|
||||
}
|
||||
//songScore += score;
|
||||
|
||||
/* if (combo > 60)
|
||||
daRating = 'sick';
|
||||
else if (combo > 12)
|
||||
daRating = 'good'
|
||||
else if (combo > 4)
|
||||
daRating = 'bad';
|
||||
*/
|
||||
|
||||
var pixelShitPart1:String = "";
|
||||
var pixelShitPart2:String = '';
|
||||
|
||||
if (PlayState.isPixelStage)
|
||||
{
|
||||
pixelShitPart1 = 'pixelUI/';
|
||||
pixelShitPart2 = '-pixel';
|
||||
}
|
||||
|
||||
rating.loadGraphic(Paths.image(pixelShitPart1 + daRating + pixelShitPart2));
|
||||
rating.screenCenter();
|
||||
rating.x = coolText.x - 40;
|
||||
rating.y -= 60;
|
||||
rating.acceleration.y = 550;
|
||||
rating.velocity.y -= FlxG.random.int(140, 175);
|
||||
rating.velocity.x -= FlxG.random.int(0, 10);
|
||||
rating.visible = !ClientPrefs.hideHud;
|
||||
|
||||
var comboSpr:FlxSprite = new FlxSprite().loadGraphic(Paths.image(pixelShitPart1 + 'combo' + pixelShitPart2));
|
||||
comboSpr.screenCenter();
|
||||
comboSpr.x = coolText.x;
|
||||
comboSpr.acceleration.y = 600;
|
||||
comboSpr.velocity.y -= 150;
|
||||
comboSpr.visible = !ClientPrefs.hideHud;
|
||||
|
||||
comboSpr.velocity.x += FlxG.random.int(1, 10);
|
||||
comboGroup.add(rating);
|
||||
|
||||
if (!PlayState.isPixelStage)
|
||||
{
|
||||
rating.setGraphicSize(Std.int(rating.width * 0.7));
|
||||
rating.antialiasing = ClientPrefs.globalAntialiasing;
|
||||
comboSpr.setGraphicSize(Std.int(comboSpr.width * 0.7));
|
||||
comboSpr.antialiasing = ClientPrefs.globalAntialiasing;
|
||||
}
|
||||
else
|
||||
{
|
||||
rating.setGraphicSize(Std.int(rating.width * PlayState.daPixelZoom * 0.7));
|
||||
comboSpr.setGraphicSize(Std.int(comboSpr.width * PlayState.daPixelZoom * 0.7));
|
||||
}
|
||||
|
||||
comboSpr.updateHitbox();
|
||||
rating.updateHitbox();
|
||||
|
||||
var seperatedScore:Array<Int> = [];
|
||||
|
||||
if(combo >= 1000) {
|
||||
seperatedScore.push(Math.floor(combo / 1000) % 10);
|
||||
}
|
||||
seperatedScore.push(Math.floor(combo / 100) % 10);
|
||||
seperatedScore.push(Math.floor(combo / 10) % 10);
|
||||
seperatedScore.push(combo % 10);
|
||||
|
||||
var daLoop:Int = 0;
|
||||
for (i in seperatedScore)
|
||||
{
|
||||
var numScore:FlxSprite = new FlxSprite().loadGraphic(Paths.image(pixelShitPart1 + 'num' + Std.int(i) + pixelShitPart2));
|
||||
numScore.screenCenter();
|
||||
numScore.x = coolText.x + (43 * daLoop) - 90;
|
||||
numScore.y += 80;
|
||||
|
||||
if (!PlayState.isPixelStage)
|
||||
{
|
||||
numScore.antialiasing = ClientPrefs.globalAntialiasing;
|
||||
numScore.setGraphicSize(Std.int(numScore.width * 0.5));
|
||||
}
|
||||
else
|
||||
{
|
||||
numScore.setGraphicSize(Std.int(numScore.width * PlayState.daPixelZoom));
|
||||
}
|
||||
numScore.updateHitbox();
|
||||
|
||||
numScore.acceleration.y = FlxG.random.int(200, 300);
|
||||
numScore.velocity.y -= FlxG.random.int(140, 160);
|
||||
numScore.velocity.x = FlxG.random.float(-5, 5);
|
||||
numScore.visible = !ClientPrefs.hideHud;
|
||||
|
||||
if (combo >= 10 || combo == 0)
|
||||
comboGroup.add(numScore);
|
||||
|
||||
FlxTween.tween(numScore, {alpha: 0}, 0.2, {
|
||||
onComplete: function(tween:FlxTween)
|
||||
{
|
||||
numScore.destroy();
|
||||
},
|
||||
startDelay: Conductor.crochet * 0.002
|
||||
});
|
||||
|
||||
daLoop++;
|
||||
}
|
||||
/*
|
||||
trace(combo);
|
||||
trace(seperatedScore);
|
||||
*/
|
||||
|
||||
coolText.text = Std.string(seperatedScore);
|
||||
// comboGroup.add(coolText);
|
||||
|
||||
FlxTween.tween(rating, {alpha: 0}, 0.2, {
|
||||
startDelay: Conductor.crochet * 0.001
|
||||
});
|
||||
|
||||
FlxTween.tween(comboSpr, {alpha: 0}, 0.2, {
|
||||
onComplete: function(tween:FlxTween)
|
||||
{
|
||||
coolText.destroy();
|
||||
comboSpr.destroy();
|
||||
|
||||
rating.destroy();
|
||||
},
|
||||
startDelay: Conductor.crochet * 0.001
|
||||
});
|
||||
}
|
||||
|
||||
private function generateStaticArrows(player:Int):Void
|
||||
{
|
||||
for (i in 0...4)
|
||||
{
|
||||
// FlxG.log.add(i);
|
||||
var babyArrow:StrumNote = new StrumNote(ClientPrefs.middleScroll ? PlayState.STRUM_X_MIDDLESCROLL : PlayState.STRUM_X, strumLine.y, i, player);
|
||||
babyArrow.alpha = 0;
|
||||
FlxTween.tween(babyArrow, {alpha: 1}, 0.5, {ease: FlxEase.circOut});
|
||||
|
||||
if (player == 1)
|
||||
{
|
||||
playerStrums.add(babyArrow);
|
||||
}
|
||||
else
|
||||
{
|
||||
opponentStrums.add(babyArrow);
|
||||
}
|
||||
|
||||
strumLineNotes.add(babyArrow);
|
||||
babyArrow.postAddedToGroup();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// For Opponent's notes glow
|
||||
function StrumPlayAnim(isDad:Bool, id:Int, time:Float) {
|
||||
var spr:StrumNote = null;
|
||||
if(isDad) {
|
||||
spr = strumLineNotes.members[id];
|
||||
} else {
|
||||
spr = playerStrums.members[id];
|
||||
}
|
||||
|
||||
if(spr != null) {
|
||||
spr.playAnim('confirm', true);
|
||||
spr.resetAnim = time;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Note splash shit, duh
|
||||
function spawnNoteSplashOnNote(note:Note) {
|
||||
if(ClientPrefs.noteSplashes && note != null) {
|
||||
var strum:StrumNote = playerStrums.members[note.noteData];
|
||||
if(strum != null) {
|
||||
spawnNoteSplash(strum.x, strum.y, note.noteData, note);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function spawnNoteSplash(x:Float, y:Float, data:Int, ?note:Note = null) {
|
||||
var skin:String = 'noteSplashes';
|
||||
if(PlayState.SONG.splashSkin != null && PlayState.SONG.splashSkin.length > 0) skin = PlayState.SONG.splashSkin;
|
||||
|
||||
var hue:Float = ClientPrefs.arrowHSV[data % 4][0] / 360;
|
||||
var sat:Float = ClientPrefs.arrowHSV[data % 4][1] / 100;
|
||||
var brt:Float = ClientPrefs.arrowHSV[data % 4][2] / 100;
|
||||
if(note != null) {
|
||||
skin = note.noteSplashTexture;
|
||||
hue = note.noteSplashHue;
|
||||
sat = note.noteSplashSat;
|
||||
brt = note.noteSplashBrt;
|
||||
}
|
||||
|
||||
var splash:NoteSplash = grpNoteSplashes.recycle(NoteSplash);
|
||||
splash.setupNoteSplash(x, y, data, skin, hue, sat, brt);
|
||||
grpNoteSplashes.add(splash);
|
||||
}
|
||||
|
||||
override function destroy() {
|
||||
FlxG.sound.music.stop();
|
||||
vocals.stop();
|
||||
vocals.destroy();
|
||||
super.destroy();
|
||||
}
|
||||
}
|
122
source/editors/MasterEditorMenu.hx
Normal file
122
source/editors/MasterEditorMenu.hx
Normal file
|
@ -0,0 +1,122 @@
|
|||
package editors;
|
||||
|
||||
#if desktop
|
||||
import Discord.DiscordClient;
|
||||
#end
|
||||
import flixel.FlxG;
|
||||
import flixel.FlxSprite;
|
||||
import flixel.addons.display.FlxGridOverlay;
|
||||
import flixel.addons.transition.FlxTransitionableState;
|
||||
import flixel.group.FlxGroup.FlxTypedGroup;
|
||||
import flixel.math.FlxMath;
|
||||
import flixel.text.FlxText;
|
||||
import flixel.util.FlxColor;
|
||||
import flixel.system.FlxSound;
|
||||
|
||||
using StringTools;
|
||||
|
||||
class MasterEditorMenu extends MusicBeatState
|
||||
{
|
||||
var options:Array<String> = [
|
||||
'Week Editor',
|
||||
'Menu Character Editor',
|
||||
'Dialogue Editor',
|
||||
'Dialogue Portrait Editor',
|
||||
'Character Editor'
|
||||
];
|
||||
private var grpTexts:FlxTypedGroup<Alphabet>;
|
||||
|
||||
private var curSelected = 0;
|
||||
|
||||
override function create()
|
||||
{
|
||||
FlxG.camera.bgColor = FlxColor.BLACK;
|
||||
#if desktop
|
||||
// Updating Discord Rich Presence
|
||||
DiscordClient.changePresence("Editors Main Menu", null);
|
||||
#end
|
||||
|
||||
var bg:FlxSprite = new FlxSprite().loadGraphic(Paths.image('menuDesat'));
|
||||
bg.scrollFactor.set();
|
||||
bg.color = 0xFF353535;
|
||||
add(bg);
|
||||
|
||||
grpTexts = new FlxTypedGroup<Alphabet>();
|
||||
add(grpTexts);
|
||||
|
||||
for (i in 0...options.length)
|
||||
{
|
||||
var leText:Alphabet = new Alphabet(0, (70 * i) + 30, options[i], true, false);
|
||||
leText.isMenuItem = true;
|
||||
leText.targetY = i;
|
||||
grpTexts.add(leText);
|
||||
}
|
||||
|
||||
changeSelection();
|
||||
super.create();
|
||||
}
|
||||
|
||||
override function update(elapsed:Float)
|
||||
{
|
||||
if (controls.UI_UP_P)
|
||||
{
|
||||
changeSelection(-1);
|
||||
}
|
||||
if (controls.UI_DOWN_P)
|
||||
{
|
||||
changeSelection(1);
|
||||
}
|
||||
|
||||
if (controls.BACK)
|
||||
{
|
||||
MusicBeatState.switchState(new MainMenuState());
|
||||
}
|
||||
|
||||
if (controls.ACCEPT)
|
||||
{
|
||||
switch(options[curSelected]) {
|
||||
case 'Character Editor':
|
||||
LoadingState.loadAndSwitchState(new CharacterEditorState(Character.DEFAULT_CHARACTER, false));
|
||||
case 'Week Editor':
|
||||
MusicBeatState.switchState(new WeekEditorState());
|
||||
case 'Menu Character Editor':
|
||||
MusicBeatState.switchState(new MenuCharacterEditorState());
|
||||
case 'Dialogue Portrait Editor':
|
||||
LoadingState.loadAndSwitchState(new DialogueCharacterEditorState(), false);
|
||||
case 'Dialogue Editor':
|
||||
LoadingState.loadAndSwitchState(new DialogueEditorState(), false);
|
||||
}
|
||||
FlxG.sound.music.volume = 0;
|
||||
FreeplayState.destroyFreeplayVocals();
|
||||
}
|
||||
|
||||
var bullShit:Int = 0;
|
||||
for (item in grpTexts.members)
|
||||
{
|
||||
item.targetY = bullShit - curSelected;
|
||||
bullShit++;
|
||||
|
||||
item.alpha = 0.6;
|
||||
// item.setGraphicSize(Std.int(item.width * 0.8));
|
||||
|
||||
if (item.targetY == 0)
|
||||
{
|
||||
item.alpha = 1;
|
||||
// item.setGraphicSize(Std.int(item.width));
|
||||
}
|
||||
}
|
||||
super.update(elapsed);
|
||||
}
|
||||
|
||||
function changeSelection(change:Int = 0)
|
||||
{
|
||||
FlxG.sound.play(Paths.sound('scrollMenu'), 0.4);
|
||||
|
||||
curSelected += change;
|
||||
|
||||
if (curSelected < 0)
|
||||
curSelected = options.length - 1;
|
||||
if (curSelected >= options.length)
|
||||
curSelected = 0;
|
||||
}
|
||||
}
|
443
source/editors/MenuCharacterEditorState.hx
Normal file
443
source/editors/MenuCharacterEditorState.hx
Normal file
|
@ -0,0 +1,443 @@
|
|||
package editors;
|
||||
|
||||
#if desktop
|
||||
import Discord.DiscordClient;
|
||||
#end
|
||||
import flixel.FlxG;
|
||||
import flixel.FlxSprite;
|
||||
import flixel.addons.display.FlxGridOverlay;
|
||||
import flixel.addons.transition.FlxTransitionableState;
|
||||
import flixel.group.FlxGroup.FlxTypedGroup;
|
||||
import flixel.math.FlxMath;
|
||||
import flixel.text.FlxText;
|
||||
import flixel.util.FlxColor;
|
||||
import flixel.system.FlxSound;
|
||||
import flixel.addons.ui.FlxInputText;
|
||||
import flixel.addons.ui.FlxUI9SliceSprite;
|
||||
import flixel.addons.ui.FlxUI;
|
||||
import flixel.addons.ui.FlxUICheckBox;
|
||||
import flixel.addons.ui.FlxUIInputText;
|
||||
import flixel.addons.ui.FlxUINumericStepper;
|
||||
import flixel.addons.ui.FlxUITabMenu;
|
||||
import flixel.ui.FlxButton;
|
||||
import MenuCharacter;
|
||||
import openfl.net.FileReference;
|
||||
import openfl.events.Event;
|
||||
import openfl.events.IOErrorEvent;
|
||||
import flash.net.FileFilter;
|
||||
import haxe.Json;
|
||||
#if sys
|
||||
import sys.io.File;
|
||||
#end
|
||||
|
||||
using StringTools;
|
||||
|
||||
class MenuCharacterEditorState extends MusicBeatState
|
||||
{
|
||||
var grpWeekCharacters:FlxTypedGroup<MenuCharacter>;
|
||||
var characterFile:MenuCharacterFile = null;
|
||||
var txtOffsets:FlxText;
|
||||
var defaultCharacters:Array<String> = ['dad', 'bf', 'gf'];
|
||||
|
||||
override function create() {
|
||||
characterFile = {
|
||||
image: 'Menu_Dad',
|
||||
scale: 1,
|
||||
position: [0, 0],
|
||||
idle_anim: 'M Dad Idle',
|
||||
confirm_anim: 'M Dad Idle'
|
||||
};
|
||||
#if desktop
|
||||
// Updating Discord Rich Presence
|
||||
DiscordClient.changePresence("Menu Character Editor", "Editting: " + characterFile.image);
|
||||
#end
|
||||
|
||||
grpWeekCharacters = new FlxTypedGroup<MenuCharacter>();
|
||||
for (char in 0...3)
|
||||
{
|
||||
var weekCharacterThing:MenuCharacter = new MenuCharacter((FlxG.width * 0.25) * (1 + char) - 150, defaultCharacters[char]);
|
||||
weekCharacterThing.y += 70;
|
||||
weekCharacterThing.alpha = 0.2;
|
||||
grpWeekCharacters.add(weekCharacterThing);
|
||||
}
|
||||
|
||||
add(new FlxSprite(0, 56).makeGraphic(FlxG.width, 386, 0xFFF9CF51));
|
||||
add(grpWeekCharacters);
|
||||
|
||||
txtOffsets = new FlxText(20, 10, 0, "[0, 0]", 32);
|
||||
txtOffsets.setFormat("VCR OSD Mono", 32, FlxColor.WHITE, CENTER);
|
||||
txtOffsets.alpha = 0.7;
|
||||
add(txtOffsets);
|
||||
|
||||
var tipText:FlxText = new FlxText(0, 540, FlxG.width,
|
||||
"Arrow Keys - Change Offset (Hold shift for 10x speed)
|
||||
\nSpace - Play \"Start Press\" animation (Boyfriend Character Type)", 16);
|
||||
tipText.setFormat(Paths.font("vcr.ttf"), 16, FlxColor.WHITE, CENTER);
|
||||
tipText.scrollFactor.set();
|
||||
add(tipText);
|
||||
|
||||
addEditorBox();
|
||||
FlxG.mouse.visible = true;
|
||||
updateCharTypeBox();
|
||||
|
||||
super.create();
|
||||
}
|
||||
|
||||
var UI_typebox:FlxUITabMenu;
|
||||
var UI_mainbox:FlxUITabMenu;
|
||||
var blockPressWhileTypingOn:Array<FlxUIInputText> = [];
|
||||
function addEditorBox() {
|
||||
var tabs = [
|
||||
{name: 'Character Type', label: 'Character Type'},
|
||||
];
|
||||
UI_typebox = new FlxUITabMenu(null, tabs, true);
|
||||
UI_typebox.resize(120, 180);
|
||||
UI_typebox.x = 100;
|
||||
UI_typebox.y = FlxG.height - UI_typebox.height - 50;
|
||||
UI_typebox.scrollFactor.set();
|
||||
addTypeUI();
|
||||
add(UI_typebox);
|
||||
|
||||
var tabs = [
|
||||
{name: 'Character', label: 'Character'},
|
||||
];
|
||||
UI_mainbox = new FlxUITabMenu(null, tabs, true);
|
||||
UI_mainbox.resize(240, 180);
|
||||
UI_mainbox.x = FlxG.width - UI_mainbox.width - 100;
|
||||
UI_mainbox.y = FlxG.height - UI_mainbox.height - 50;
|
||||
UI_mainbox.scrollFactor.set();
|
||||
addCharacterUI();
|
||||
add(UI_mainbox);
|
||||
|
||||
var loadButton:FlxButton = new FlxButton(0, 480, "Load Character", function() {
|
||||
loadCharacter();
|
||||
});
|
||||
loadButton.screenCenter(X);
|
||||
loadButton.x -= 60;
|
||||
add(loadButton);
|
||||
|
||||
var saveButton:FlxButton = new FlxButton(0, 480, "Save Character", function() {
|
||||
saveCharacter();
|
||||
});
|
||||
saveButton.screenCenter(X);
|
||||
saveButton.x += 60;
|
||||
add(saveButton);
|
||||
}
|
||||
|
||||
var opponentCheckbox:FlxUICheckBox;
|
||||
var boyfriendCheckbox:FlxUICheckBox;
|
||||
var girlfriendCheckbox:FlxUICheckBox;
|
||||
var curTypeSelected:Int = 0; //0 = Dad, 1 = BF, 2 = GF
|
||||
function addTypeUI() {
|
||||
var tab_group = new FlxUI(null, UI_typebox);
|
||||
tab_group.name = "Character Type";
|
||||
|
||||
opponentCheckbox = new FlxUICheckBox(10, 20, null, null, "Opponent", 100);
|
||||
opponentCheckbox.callback = function()
|
||||
{
|
||||
curTypeSelected = 0;
|
||||
updateCharTypeBox();
|
||||
};
|
||||
|
||||
boyfriendCheckbox = new FlxUICheckBox(opponentCheckbox.x, opponentCheckbox.y + 40, null, null, "Boyfriend", 100);
|
||||
boyfriendCheckbox.callback = function()
|
||||
{
|
||||
curTypeSelected = 1;
|
||||
updateCharTypeBox();
|
||||
};
|
||||
|
||||
girlfriendCheckbox = new FlxUICheckBox(boyfriendCheckbox.x, boyfriendCheckbox.y + 40, null, null, "Girlfriend", 100);
|
||||
girlfriendCheckbox.callback = function()
|
||||
{
|
||||
curTypeSelected = 2;
|
||||
updateCharTypeBox();
|
||||
};
|
||||
|
||||
tab_group.add(opponentCheckbox);
|
||||
tab_group.add(boyfriendCheckbox);
|
||||
tab_group.add(girlfriendCheckbox);
|
||||
UI_typebox.addGroup(tab_group);
|
||||
}
|
||||
|
||||
var imageInputText:FlxUIInputText;
|
||||
var idleInputText:FlxUIInputText;
|
||||
var confirmInputText:FlxUIInputText;
|
||||
var confirmDescText:FlxText;
|
||||
var scaleStepper:FlxUINumericStepper;
|
||||
function addCharacterUI() {
|
||||
var tab_group = new FlxUI(null, UI_mainbox);
|
||||
tab_group.name = "Character";
|
||||
|
||||
imageInputText = new FlxUIInputText(10, 20, 80, characterFile.image, 8);
|
||||
blockPressWhileTypingOn.push(imageInputText);
|
||||
idleInputText = new FlxUIInputText(10, imageInputText.y + 35, 100, characterFile.idle_anim, 8);
|
||||
blockPressWhileTypingOn.push(idleInputText);
|
||||
confirmInputText = new FlxUIInputText(10, idleInputText.y + 35, 100, characterFile.confirm_anim, 8);
|
||||
blockPressWhileTypingOn.push(confirmInputText);
|
||||
|
||||
var reloadImageButton:FlxButton = new FlxButton(10, confirmInputText.y + 30, "Reload Char", function() {
|
||||
reloadSelectedCharacter();
|
||||
});
|
||||
|
||||
scaleStepper = new FlxUINumericStepper(140, imageInputText.y, 0.05, 1, 0.1, 30, 2);
|
||||
|
||||
confirmDescText = new FlxText(10, confirmInputText.y - 18, 0, 'Start Press animation on the .XML:');
|
||||
tab_group.add(new FlxText(10, imageInputText.y - 18, 0, 'Image file name:'));
|
||||
tab_group.add(new FlxText(10, idleInputText.y - 18, 0, 'Idle animation on the .XML:'));
|
||||
tab_group.add(new FlxText(scaleStepper.x, scaleStepper.y - 18, 0, 'Scale:'));
|
||||
tab_group.add(reloadImageButton);
|
||||
tab_group.add(confirmDescText);
|
||||
tab_group.add(imageInputText);
|
||||
tab_group.add(idleInputText);
|
||||
tab_group.add(confirmInputText);
|
||||
tab_group.add(scaleStepper);
|
||||
UI_mainbox.addGroup(tab_group);
|
||||
}
|
||||
|
||||
function updateCharTypeBox() {
|
||||
opponentCheckbox.checked = false;
|
||||
boyfriendCheckbox.checked = false;
|
||||
girlfriendCheckbox.checked = false;
|
||||
|
||||
switch(curTypeSelected) {
|
||||
case 0:
|
||||
opponentCheckbox.checked = true;
|
||||
case 1:
|
||||
boyfriendCheckbox.checked = true;
|
||||
case 2:
|
||||
girlfriendCheckbox.checked = true;
|
||||
}
|
||||
|
||||
updateCharacters();
|
||||
}
|
||||
|
||||
function updateCharacters() {
|
||||
for (i in 0...3) {
|
||||
var char:MenuCharacter = grpWeekCharacters.members[i];
|
||||
char.alpha = 0.2;
|
||||
char.character = '';
|
||||
char.changeCharacter(defaultCharacters[i]);
|
||||
}
|
||||
reloadSelectedCharacter();
|
||||
}
|
||||
|
||||
function reloadSelectedCharacter() {
|
||||
var char:MenuCharacter = grpWeekCharacters.members[curTypeSelected];
|
||||
|
||||
char.alpha = 1;
|
||||
char.frames = Paths.getSparrowAtlas('menucharacters/' + characterFile.image);
|
||||
char.animation.addByPrefix('idle', characterFile.idle_anim, 24);
|
||||
if(curTypeSelected == 1) char.animation.addByPrefix('confirm', characterFile.confirm_anim, 24, false);
|
||||
|
||||
char.scale.set(characterFile.scale, characterFile.scale);
|
||||
char.updateHitbox();
|
||||
char.animation.play('idle');
|
||||
|
||||
confirmDescText.visible = (curTypeSelected == 1);
|
||||
confirmInputText.visible = (curTypeSelected == 1);
|
||||
updateOffset();
|
||||
|
||||
#if desktop
|
||||
// Updating Discord Rich Presence
|
||||
DiscordClient.changePresence("Menu Character Editor", "Editting: " + characterFile.image);
|
||||
#end
|
||||
}
|
||||
|
||||
override function getEvent(id:String, sender:Dynamic, data:Dynamic, ?params:Array<Dynamic>) {
|
||||
if(id == FlxUIInputText.CHANGE_EVENT && (sender is FlxUIInputText)) {
|
||||
if(sender == imageInputText) {
|
||||
characterFile.image = imageInputText.text;
|
||||
} else if(sender == idleInputText) {
|
||||
characterFile.idle_anim = idleInputText.text;
|
||||
} else if(sender == confirmInputText) {
|
||||
characterFile.confirm_anim = confirmInputText.text;
|
||||
}
|
||||
} else if(id == FlxUINumericStepper.CHANGE_EVENT && (sender is FlxUINumericStepper)) {
|
||||
if (sender == scaleStepper) {
|
||||
characterFile.scale = scaleStepper.value;
|
||||
reloadSelectedCharacter();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override function update(elapsed:Float) {
|
||||
var blockInput:Bool = false;
|
||||
for (inputText in blockPressWhileTypingOn) {
|
||||
if(inputText.hasFocus) {
|
||||
FlxG.sound.muteKeys = [];
|
||||
FlxG.sound.volumeDownKeys = [];
|
||||
FlxG.sound.volumeUpKeys = [];
|
||||
blockInput = true;
|
||||
|
||||
if(FlxG.keys.justPressed.ENTER) inputText.hasFocus = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if(!blockInput) {
|
||||
FlxG.sound.muteKeys = TitleState.muteKeys;
|
||||
FlxG.sound.volumeDownKeys = TitleState.volumeDownKeys;
|
||||
FlxG.sound.volumeUpKeys = TitleState.volumeUpKeys;
|
||||
if(FlxG.keys.justPressed.ESCAPE) {
|
||||
FlxG.mouse.visible = false;
|
||||
MusicBeatState.switchState(new editors.MasterEditorMenu());
|
||||
FlxG.sound.playMusic(Paths.music('freakyMenu'));
|
||||
}
|
||||
|
||||
var shiftMult:Int = 1;
|
||||
if(FlxG.keys.pressed.SHIFT) shiftMult = 10;
|
||||
|
||||
if(FlxG.keys.justPressed.LEFT) {
|
||||
characterFile.position[0] += shiftMult;
|
||||
updateOffset();
|
||||
}
|
||||
if(FlxG.keys.justPressed.RIGHT) {
|
||||
characterFile.position[0] -= shiftMult;
|
||||
updateOffset();
|
||||
}
|
||||
if(FlxG.keys.justPressed.UP) {
|
||||
characterFile.position[1] += shiftMult;
|
||||
updateOffset();
|
||||
}
|
||||
if(FlxG.keys.justPressed.DOWN) {
|
||||
characterFile.position[1] -= shiftMult;
|
||||
updateOffset();
|
||||
}
|
||||
|
||||
if(FlxG.keys.justPressed.SPACE && curTypeSelected == 1) {
|
||||
grpWeekCharacters.members[curTypeSelected].animation.play('confirm', true);
|
||||
}
|
||||
}
|
||||
|
||||
var char:MenuCharacter = grpWeekCharacters.members[1];
|
||||
if(char.animation.curAnim != null && char.animation.curAnim.name == 'confirm' && char.animation.curAnim.finished) {
|
||||
char.animation.play('idle', true);
|
||||
}
|
||||
|
||||
super.update(elapsed);
|
||||
}
|
||||
|
||||
function updateOffset() {
|
||||
var char:MenuCharacter = grpWeekCharacters.members[curTypeSelected];
|
||||
char.offset.set(characterFile.position[0], characterFile.position[1]);
|
||||
txtOffsets.text = '' + characterFile.position;
|
||||
}
|
||||
|
||||
var _file:FileReference = null;
|
||||
function loadCharacter() {
|
||||
var jsonFilter:FileFilter = new FileFilter('JSON', 'json');
|
||||
_file = new FileReference();
|
||||
_file.addEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.addEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.addEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
_file.browse([jsonFilter]);
|
||||
}
|
||||
|
||||
function onLoadComplete(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
|
||||
#if sys
|
||||
var fullPath:String = null;
|
||||
var jsonLoaded = cast Json.parse(Json.stringify(_file)); //Exploit(???) for accessing a private variable
|
||||
if(jsonLoaded.__path != null) fullPath = jsonLoaded.__path; //I'm either a genious or dangerously dumb
|
||||
|
||||
if(fullPath != null) {
|
||||
var rawJson:String = File.getContent(fullPath);
|
||||
if(rawJson != null) {
|
||||
var loadedChar:MenuCharacterFile = cast Json.parse(rawJson);
|
||||
if(loadedChar.idle_anim != null && loadedChar.confirm_anim != null) //Make sure it's really a character
|
||||
{
|
||||
var cutName:String = _file.name.substr(0, _file.name.length - 5);
|
||||
trace("Successfully loaded file: " + cutName);
|
||||
characterFile = loadedChar;
|
||||
reloadSelectedCharacter();
|
||||
imageInputText.text = characterFile.image;
|
||||
idleInputText.text = characterFile.image;
|
||||
confirmInputText.text = characterFile.image;
|
||||
scaleStepper.value = characterFile.scale;
|
||||
updateOffset();
|
||||
_file = null;
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
_file = null;
|
||||
#else
|
||||
trace("File couldn't be loaded! You aren't on Desktop, are you?");
|
||||
#end
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the save file dialog is cancelled.
|
||||
*/
|
||||
function onLoadCancel(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
_file = null;
|
||||
trace("Cancelled file loading.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Called if there is an error while saving the gameplay recording.
|
||||
*/
|
||||
function onLoadError(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
_file = null;
|
||||
trace("Problem loading file");
|
||||
}
|
||||
|
||||
function saveCharacter() {
|
||||
var data:String = Json.stringify(characterFile, "\t");
|
||||
if (data.length > 0)
|
||||
{
|
||||
var splittedImage:Array<String> = imageInputText.text.trim().split('_');
|
||||
var characterName:String = splittedImage[splittedImage.length-1].toLowerCase().replace(' ', '');
|
||||
|
||||
_file = new FileReference();
|
||||
_file.addEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.addEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.addEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file.save(data, characterName + ".json");
|
||||
}
|
||||
}
|
||||
|
||||
function onSaveComplete(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file = null;
|
||||
FlxG.log.notice("Successfully saved file.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the save file dialog is cancelled.
|
||||
*/
|
||||
function onSaveCancel(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file = null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Called if there is an error while saving the gameplay recording.
|
||||
*/
|
||||
function onSaveError(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file = null;
|
||||
FlxG.log.error("Problem saving file");
|
||||
}
|
||||
}
|
796
source/editors/WeekEditorState.hx
Normal file
796
source/editors/WeekEditorState.hx
Normal file
|
@ -0,0 +1,796 @@
|
|||
package editors;
|
||||
|
||||
#if desktop
|
||||
import Discord.DiscordClient;
|
||||
#end
|
||||
import flixel.FlxG;
|
||||
import flixel.FlxSprite;
|
||||
import flixel.addons.display.FlxGridOverlay;
|
||||
import flixel.addons.transition.FlxTransitionableState;
|
||||
import flixel.group.FlxGroup.FlxTypedGroup;
|
||||
import flixel.math.FlxMath;
|
||||
import flixel.text.FlxText;
|
||||
import flixel.util.FlxColor;
|
||||
import flixel.system.FlxSound;
|
||||
import openfl.utils.Assets;
|
||||
import flixel.addons.ui.FlxInputText;
|
||||
import flixel.addons.ui.FlxUI9SliceSprite;
|
||||
import flixel.addons.ui.FlxUI;
|
||||
import flixel.addons.ui.FlxUICheckBox;
|
||||
import flixel.addons.ui.FlxUIInputText;
|
||||
import flixel.addons.ui.FlxUINumericStepper;
|
||||
import flixel.addons.ui.FlxUITabMenu;
|
||||
import flixel.ui.FlxButton;
|
||||
import openfl.net.FileReference;
|
||||
import openfl.events.Event;
|
||||
import openfl.events.IOErrorEvent;
|
||||
import flash.net.FileFilter;
|
||||
import lime.system.Clipboard;
|
||||
import haxe.Json;
|
||||
#if sys
|
||||
import sys.io.File;
|
||||
import sys.FileSystem;
|
||||
#end
|
||||
import WeekData;
|
||||
|
||||
using StringTools;
|
||||
|
||||
class WeekEditorState extends MusicBeatState
|
||||
{
|
||||
var txtWeekTitle:FlxText;
|
||||
var bgSprite:FlxSprite;
|
||||
var lock:FlxSprite;
|
||||
var txtTracklist:FlxText;
|
||||
var grpWeekCharacters:FlxTypedGroup<MenuCharacter>;
|
||||
var weekThing:MenuItem;
|
||||
var missingFileText:FlxText;
|
||||
|
||||
var weekFile:WeekFile = null;
|
||||
public function new(weekFile:WeekFile = null)
|
||||
{
|
||||
super();
|
||||
this.weekFile = WeekData.createWeekFile();
|
||||
if(weekFile != null) this.weekFile = weekFile;
|
||||
else weekFileName = 'week1';
|
||||
}
|
||||
|
||||
override function create() {
|
||||
txtWeekTitle = new FlxText(FlxG.width * 0.7, 10, 0, "", 32);
|
||||
txtWeekTitle.setFormat("VCR OSD Mono", 32, FlxColor.WHITE, RIGHT);
|
||||
txtWeekTitle.alpha = 0.7;
|
||||
|
||||
var ui_tex = Paths.getSparrowAtlas('campaign_menu_UI_assets');
|
||||
var bgYellow:FlxSprite = new FlxSprite(0, 56).makeGraphic(FlxG.width, 386, 0xFFF9CF51);
|
||||
bgSprite = new FlxSprite(0, 56);
|
||||
bgSprite.antialiasing = ClientPrefs.globalAntialiasing;
|
||||
|
||||
weekThing = new MenuItem(0, bgSprite.y + 396, weekFileName);
|
||||
weekThing.y += weekThing.height + 20;
|
||||
weekThing.antialiasing = ClientPrefs.globalAntialiasing;
|
||||
add(weekThing);
|
||||
|
||||
var blackBarThingie:FlxSprite = new FlxSprite().makeGraphic(FlxG.width, 56, FlxColor.BLACK);
|
||||
add(blackBarThingie);
|
||||
|
||||
grpWeekCharacters = new FlxTypedGroup<MenuCharacter>();
|
||||
|
||||
lock = new FlxSprite();
|
||||
lock.frames = ui_tex;
|
||||
lock.animation.addByPrefix('lock', 'lock');
|
||||
lock.animation.play('lock');
|
||||
lock.antialiasing = ClientPrefs.globalAntialiasing;
|
||||
add(lock);
|
||||
|
||||
missingFileText = new FlxText(0, 0, FlxG.width, "");
|
||||
missingFileText.setFormat(Paths.font("vcr.ttf"), 24, FlxColor.WHITE, CENTER, FlxTextBorderStyle.OUTLINE, FlxColor.BLACK);
|
||||
missingFileText.borderSize = 2;
|
||||
missingFileText.visible = false;
|
||||
add(missingFileText);
|
||||
|
||||
var charArray:Array<String> = weekFile.weekCharacters;
|
||||
for (char in 0...3)
|
||||
{
|
||||
var weekCharacterThing:MenuCharacter = new MenuCharacter((FlxG.width * 0.25) * (1 + char) - 150, charArray[char]);
|
||||
weekCharacterThing.y += 70;
|
||||
grpWeekCharacters.add(weekCharacterThing);
|
||||
}
|
||||
|
||||
add(bgYellow);
|
||||
add(bgSprite);
|
||||
add(grpWeekCharacters);
|
||||
|
||||
var tracksSprite:FlxSprite = new FlxSprite(FlxG.width * 0.07, bgSprite.y + 435).loadGraphic(Paths.image('Menu_Tracks'));
|
||||
tracksSprite.antialiasing = ClientPrefs.globalAntialiasing;
|
||||
add(tracksSprite);
|
||||
|
||||
txtTracklist = new FlxText(FlxG.width * 0.05, tracksSprite.y + 60, 0, "", 32);
|
||||
txtTracklist.alignment = CENTER;
|
||||
txtTracklist.font = Paths.font("vcr.ttf");
|
||||
txtTracklist.color = 0xFFe55777;
|
||||
add(txtTracklist);
|
||||
add(txtWeekTitle);
|
||||
|
||||
addEditorBox();
|
||||
reloadAllShit();
|
||||
|
||||
FlxG.mouse.visible = true;
|
||||
|
||||
super.create();
|
||||
}
|
||||
|
||||
var UI_box:FlxUITabMenu;
|
||||
var blockPressWhileTypingOn:Array<FlxUIInputText> = [];
|
||||
function addEditorBox() {
|
||||
var tabs = [
|
||||
{name: 'Week', label: 'Week'},
|
||||
{name: 'Lock', label: 'Lock'},
|
||||
];
|
||||
UI_box = new FlxUITabMenu(null, tabs, true);
|
||||
UI_box.resize(250, 375);
|
||||
UI_box.x = FlxG.width - UI_box.width;
|
||||
UI_box.y = FlxG.height - UI_box.height;
|
||||
UI_box.scrollFactor.set();
|
||||
addWeekUI();
|
||||
addLockUI();
|
||||
|
||||
UI_box.selected_tab_id = 'Week';
|
||||
add(UI_box);
|
||||
|
||||
var loadWeekButton:FlxButton = new FlxButton(0, 650, "Load Week", function() {
|
||||
loadWeek();
|
||||
});
|
||||
loadWeekButton.screenCenter(X);
|
||||
loadWeekButton.x -= 120;
|
||||
add(loadWeekButton);
|
||||
|
||||
var freeplayButton:FlxButton = new FlxButton(0, 650, "Freeplay", function() {
|
||||
MusicBeatState.switchState(new WeekEditorFreeplayState(weekFile));
|
||||
|
||||
});
|
||||
freeplayButton.screenCenter(X);
|
||||
add(freeplayButton);
|
||||
|
||||
var saveWeekButton:FlxButton = new FlxButton(0, 650, "Save Week", function() {
|
||||
saveWeek(weekFile);
|
||||
});
|
||||
saveWeekButton.screenCenter(X);
|
||||
saveWeekButton.x += 120;
|
||||
add(saveWeekButton);
|
||||
}
|
||||
|
||||
var songsInputText:FlxUIInputText;
|
||||
var backgroundInputText:FlxUIInputText;
|
||||
var displayNameInputText:FlxUIInputText;
|
||||
var weekNameInputText:FlxUIInputText;
|
||||
var weekFileInputText:FlxUIInputText;
|
||||
|
||||
var opponentInputText:FlxUIInputText;
|
||||
var boyfriendInputText:FlxUIInputText;
|
||||
var girlfriendInputText:FlxUIInputText;
|
||||
|
||||
var hideCheckbox:FlxUICheckBox;
|
||||
|
||||
public static var weekFileName:String = 'week1';
|
||||
|
||||
function addWeekUI() {
|
||||
var tab_group = new FlxUI(null, UI_box);
|
||||
tab_group.name = "Week";
|
||||
|
||||
songsInputText = new FlxUIInputText(10, 30, 200, '', 8);
|
||||
blockPressWhileTypingOn.push(songsInputText);
|
||||
|
||||
opponentInputText = new FlxUIInputText(10, songsInputText.y + 40, 70, '', 8);
|
||||
blockPressWhileTypingOn.push(opponentInputText);
|
||||
boyfriendInputText = new FlxUIInputText(opponentInputText.x + 75, opponentInputText.y, 70, '', 8);
|
||||
blockPressWhileTypingOn.push(boyfriendInputText);
|
||||
girlfriendInputText = new FlxUIInputText(boyfriendInputText.x + 75, opponentInputText.y, 70, '', 8);
|
||||
blockPressWhileTypingOn.push(girlfriendInputText);
|
||||
|
||||
backgroundInputText = new FlxUIInputText(10, opponentInputText.y + 40, 120, '', 8);
|
||||
blockPressWhileTypingOn.push(backgroundInputText);
|
||||
|
||||
|
||||
displayNameInputText = new FlxUIInputText(10, backgroundInputText.y + 60, 200, '', 8);
|
||||
blockPressWhileTypingOn.push(backgroundInputText);
|
||||
|
||||
weekNameInputText = new FlxUIInputText(10, displayNameInputText.y + 60, 150, '', 8);
|
||||
blockPressWhileTypingOn.push(weekNameInputText);
|
||||
|
||||
weekFileInputText = new FlxUIInputText(10, weekNameInputText.y + 40, 100, '', 8);
|
||||
blockPressWhileTypingOn.push(weekFileInputText);
|
||||
reloadWeekThing();
|
||||
|
||||
hideCheckbox = new FlxUICheckBox(10, weekFileInputText.y + 40, null, null, "Hide Week from Story Mode?", 100);
|
||||
hideCheckbox.callback = function()
|
||||
{
|
||||
weekFile.hideStoryMode = hideCheckbox.checked;
|
||||
};
|
||||
|
||||
tab_group.add(new FlxText(songsInputText.x, songsInputText.y - 18, 0, 'Songs:'));
|
||||
tab_group.add(new FlxText(opponentInputText.x, opponentInputText.y - 18, 0, 'Characters:'));
|
||||
tab_group.add(new FlxText(backgroundInputText.x, backgroundInputText.y - 18, 0, 'Background Asset:'));
|
||||
tab_group.add(new FlxText(displayNameInputText.x, displayNameInputText.y - 18, 0, 'Display Name:'));
|
||||
tab_group.add(new FlxText(weekNameInputText.x, weekNameInputText.y - 18, 0, 'Week Name (for Reset Score Menu):'));
|
||||
tab_group.add(new FlxText(weekFileInputText.x, weekFileInputText.y - 18, 0, 'Week File:'));
|
||||
|
||||
tab_group.add(songsInputText);
|
||||
tab_group.add(opponentInputText);
|
||||
tab_group.add(boyfriendInputText);
|
||||
tab_group.add(girlfriendInputText);
|
||||
tab_group.add(backgroundInputText);
|
||||
|
||||
tab_group.add(displayNameInputText);
|
||||
tab_group.add(weekNameInputText);
|
||||
tab_group.add(weekFileInputText);
|
||||
tab_group.add(hideCheckbox);
|
||||
UI_box.addGroup(tab_group);
|
||||
}
|
||||
|
||||
var weekBeforeInputText:FlxUIInputText;
|
||||
var lockedCheckbox:FlxUICheckBox;
|
||||
|
||||
function addLockUI() {
|
||||
var tab_group = new FlxUI(null, UI_box);
|
||||
tab_group.name = "Lock";
|
||||
|
||||
lockedCheckbox = new FlxUICheckBox(10, 30, null, null, "Week starts Locked", 100);
|
||||
lockedCheckbox.callback = function()
|
||||
{
|
||||
weekFile.startUnlocked = !lockedCheckbox.checked;
|
||||
lock.visible = lockedCheckbox.checked;
|
||||
};
|
||||
|
||||
weekBeforeInputText = new FlxUIInputText(10, lockedCheckbox.y + 55, 100, '', 8);
|
||||
blockPressWhileTypingOn.push(weekBeforeInputText);
|
||||
|
||||
tab_group.add(new FlxText(weekBeforeInputText.x, weekBeforeInputText.y - 28, 0, 'Week File name of the Week you have\nto finish for Unlocking:'));
|
||||
tab_group.add(weekBeforeInputText);
|
||||
tab_group.add(lockedCheckbox);
|
||||
UI_box.addGroup(tab_group);
|
||||
}
|
||||
|
||||
//Used on onCreate and when you load a week
|
||||
function reloadAllShit() {
|
||||
var weekString:String = weekFile.songs[0][0];
|
||||
for (i in 1...weekFile.songs.length) {
|
||||
weekString += ', ' + weekFile.songs[i][0];
|
||||
}
|
||||
songsInputText.text = weekString;
|
||||
backgroundInputText.text = weekFile.weekBackground;
|
||||
displayNameInputText.text = weekFile.storyName;
|
||||
weekNameInputText.text = weekFile.weekName;
|
||||
weekFileInputText.text = weekFileName;
|
||||
|
||||
opponentInputText.text = weekFile.weekCharacters[0];
|
||||
boyfriendInputText.text = weekFile.weekCharacters[1];
|
||||
girlfriendInputText.text = weekFile.weekCharacters[2];
|
||||
|
||||
hideCheckbox.checked = weekFile.hideStoryMode;
|
||||
|
||||
weekBeforeInputText.text = weekFile.weekBefore;
|
||||
lockedCheckbox.checked = !weekFile.startUnlocked;
|
||||
lock.visible = lockedCheckbox.checked;
|
||||
|
||||
reloadBG();
|
||||
reloadWeekThing();
|
||||
updateText();
|
||||
}
|
||||
|
||||
function updateText()
|
||||
{
|
||||
for (i in 0...grpWeekCharacters.length) {
|
||||
grpWeekCharacters.members[i].changeCharacter(weekFile.weekCharacters[i]);
|
||||
}
|
||||
|
||||
var stringThing:Array<String> = [];
|
||||
for (i in 0...weekFile.songs.length) {
|
||||
stringThing.push(weekFile.songs[i][0]);
|
||||
}
|
||||
|
||||
txtTracklist.text = '';
|
||||
for (i in 0...stringThing.length)
|
||||
{
|
||||
txtTracklist.text += stringThing[i] + '\n';
|
||||
}
|
||||
|
||||
txtTracklist.text = txtTracklist.text.toUpperCase();
|
||||
|
||||
txtTracklist.screenCenter(X);
|
||||
txtTracklist.x -= FlxG.width * 0.35;
|
||||
|
||||
txtWeekTitle.text = weekFile.storyName.toUpperCase();
|
||||
txtWeekTitle.x = FlxG.width - (txtWeekTitle.width + 10);
|
||||
}
|
||||
|
||||
function reloadBG() {
|
||||
bgSprite.visible = true;
|
||||
var assetName:String = weekFile.weekBackground;
|
||||
|
||||
var isMissing:Bool = true;
|
||||
if(assetName != null && assetName.length > 0) {
|
||||
if( #if MODS_ALLOWED FileSystem.exists(Paths.modsImages('menubackgrounds/menu_' + assetName)) || #end
|
||||
Assets.exists(Paths.image('menubackgrounds/menu_' + assetName), IMAGE)) {
|
||||
bgSprite.loadGraphic(Paths.image('menubackgrounds/menu_' + assetName));
|
||||
isMissing = false;
|
||||
}
|
||||
}
|
||||
|
||||
if(isMissing) {
|
||||
bgSprite.visible = false;
|
||||
}
|
||||
}
|
||||
|
||||
function reloadWeekThing() {
|
||||
weekThing.visible = true;
|
||||
missingFileText.visible = false;
|
||||
var assetName:String = weekFileInputText.text.trim();
|
||||
|
||||
var isMissing:Bool = true;
|
||||
if(assetName != null && assetName.length > 0) {
|
||||
if( #if MODS_ALLOWED FileSystem.exists(Paths.modsImages('storymenu/' + assetName)) || #end
|
||||
Assets.exists(Paths.image('storymenu/' + assetName), IMAGE)) {
|
||||
weekThing.loadGraphic(Paths.image('storymenu/' + assetName));
|
||||
isMissing = false;
|
||||
}
|
||||
}
|
||||
|
||||
if(isMissing) {
|
||||
weekThing.visible = false;
|
||||
missingFileText.visible = true;
|
||||
missingFileText.text = 'MISSING FILE: images/storymenu/' + assetName + '.png';
|
||||
}
|
||||
recalculateStuffPosition();
|
||||
|
||||
#if desktop
|
||||
// Updating Discord Rich Presence
|
||||
DiscordClient.changePresence("Week Editor", "Editting: " + weekFileName);
|
||||
#end
|
||||
}
|
||||
|
||||
override function getEvent(id:String, sender:Dynamic, data:Dynamic, ?params:Array<Dynamic>) {
|
||||
if(id == FlxUIInputText.CHANGE_EVENT && (sender is FlxUIInputText)) {
|
||||
if(sender == weekFileInputText) {
|
||||
weekFileName = weekFileInputText.text.trim();
|
||||
reloadWeekThing();
|
||||
} else if(sender == opponentInputText || sender == boyfriendInputText || sender == girlfriendInputText) {
|
||||
weekFile.weekCharacters[0] = opponentInputText.text.trim();
|
||||
weekFile.weekCharacters[1] = boyfriendInputText.text.trim();
|
||||
weekFile.weekCharacters[2] = girlfriendInputText.text.trim();
|
||||
updateText();
|
||||
} else if(sender == backgroundInputText) {
|
||||
weekFile.weekBackground = backgroundInputText.text.trim();
|
||||
reloadBG();
|
||||
} else if(sender == displayNameInputText) {
|
||||
weekFile.storyName = displayNameInputText.text.trim();
|
||||
updateText();
|
||||
} else if(sender == weekNameInputText) {
|
||||
weekFile.weekName = weekNameInputText.text.trim();
|
||||
} else if(sender == songsInputText) {
|
||||
var splittedText:Array<String> = songsInputText.text.trim().split(',');
|
||||
for (i in 0...splittedText.length) {
|
||||
splittedText[i] = splittedText[i].trim();
|
||||
}
|
||||
|
||||
while(splittedText.length < weekFile.songs.length) {
|
||||
weekFile.songs.pop();
|
||||
}
|
||||
|
||||
for (i in 0...splittedText.length) {
|
||||
if(i >= weekFile.songs.length) { //Add new song
|
||||
weekFile.songs.push([splittedText[i], 'dad', [146, 113, 253]]);
|
||||
} else { //Edit song
|
||||
weekFile.songs[i][0] = splittedText[i];
|
||||
if(weekFile.songs[i][1] == null || weekFile.songs[i][1]) {
|
||||
weekFile.songs[i][1] = 'dad';
|
||||
weekFile.songs[i][2] = [146, 113, 253];
|
||||
}
|
||||
}
|
||||
}
|
||||
updateText();
|
||||
} else if(sender == weekBeforeInputText) {
|
||||
weekFile.weekBefore = weekBeforeInputText.text.trim();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override function update(elapsed:Float)
|
||||
{
|
||||
if(loadedWeek != null) {
|
||||
weekFile = loadedWeek;
|
||||
loadedWeek = null;
|
||||
|
||||
reloadAllShit();
|
||||
}
|
||||
|
||||
var blockInput:Bool = false;
|
||||
for (inputText in blockPressWhileTypingOn) {
|
||||
if(inputText.hasFocus) {
|
||||
FlxG.sound.muteKeys = [];
|
||||
FlxG.sound.volumeDownKeys = [];
|
||||
FlxG.sound.volumeUpKeys = [];
|
||||
blockInput = true;
|
||||
|
||||
if(FlxG.keys.justPressed.ENTER) inputText.hasFocus = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if(!blockInput) {
|
||||
FlxG.sound.muteKeys = TitleState.muteKeys;
|
||||
FlxG.sound.volumeDownKeys = TitleState.volumeDownKeys;
|
||||
FlxG.sound.volumeUpKeys = TitleState.volumeUpKeys;
|
||||
if(FlxG.keys.justPressed.ESCAPE) {
|
||||
FlxG.mouse.visible = false;
|
||||
MusicBeatState.switchState(new editors.MasterEditorMenu());
|
||||
FlxG.sound.playMusic(Paths.music('freakyMenu'));
|
||||
}
|
||||
}
|
||||
|
||||
super.update(elapsed);
|
||||
|
||||
lock.y = weekThing.y;
|
||||
missingFileText.y = weekThing.y + 36;
|
||||
}
|
||||
|
||||
function recalculateStuffPosition() {
|
||||
weekThing.screenCenter(X);
|
||||
lock.x = weekThing.width + 10 + weekThing.x;
|
||||
}
|
||||
|
||||
private static var _file:FileReference;
|
||||
public static function loadWeek() {
|
||||
var jsonFilter:FileFilter = new FileFilter('JSON', 'json');
|
||||
_file = new FileReference();
|
||||
_file.addEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.addEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.addEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
_file.browse([jsonFilter]);
|
||||
}
|
||||
|
||||
public static var loadedWeek:WeekFile = null;
|
||||
public static var loadError:Bool = false;
|
||||
private static function onLoadComplete(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
|
||||
#if sys
|
||||
var fullPath:String = null;
|
||||
var jsonLoaded = cast Json.parse(Json.stringify(_file)); //Exploit(???) for accessing a private variable
|
||||
if(jsonLoaded.__path != null) fullPath = jsonLoaded.__path; //I'm either a genious or dangerously dumb
|
||||
|
||||
if(fullPath != null) {
|
||||
var rawJson:String = File.getContent(fullPath);
|
||||
if(rawJson != null) {
|
||||
loadedWeek = cast Json.parse(rawJson);
|
||||
if(loadedWeek.weekCharacters != null && loadedWeek.weekName != null) //Make sure it's really a week
|
||||
{
|
||||
var cutName:String = _file.name.substr(0, _file.name.length - 5);
|
||||
trace("Successfully loaded file: " + cutName);
|
||||
loadError = false;
|
||||
|
||||
weekFileName = cutName;
|
||||
_file = null;
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
loadError = true;
|
||||
loadedWeek = null;
|
||||
_file = null;
|
||||
#else
|
||||
trace("File couldn't be loaded! You aren't on Desktop, are you?");
|
||||
#end
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the save file dialog is cancelled.
|
||||
*/
|
||||
private static function onLoadCancel(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
_file = null;
|
||||
trace("Cancelled file loading.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Called if there is an error while saving the gameplay recording.
|
||||
*/
|
||||
private static function onLoadError(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.SELECT, onLoadComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onLoadCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onLoadError);
|
||||
_file = null;
|
||||
trace("Problem loading file");
|
||||
}
|
||||
|
||||
public static function saveWeek(weekFile:WeekFile) {
|
||||
var data:String = Json.stringify(weekFile, "\t");
|
||||
if (data.length > 0)
|
||||
{
|
||||
_file = new FileReference();
|
||||
_file.addEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.addEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.addEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file.save(data, weekFileName + ".json");
|
||||
}
|
||||
}
|
||||
|
||||
private static function onSaveComplete(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file = null;
|
||||
FlxG.log.notice("Successfully saved file.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the save file dialog is cancelled.
|
||||
*/
|
||||
private static function onSaveCancel(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file = null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Called if there is an error while saving the gameplay recording.
|
||||
*/
|
||||
private static function onSaveError(_):Void
|
||||
{
|
||||
_file.removeEventListener(Event.COMPLETE, onSaveComplete);
|
||||
_file.removeEventListener(Event.CANCEL, onSaveCancel);
|
||||
_file.removeEventListener(IOErrorEvent.IO_ERROR, onSaveError);
|
||||
_file = null;
|
||||
FlxG.log.error("Problem saving file");
|
||||
}
|
||||
}
|
||||
|
||||
class WeekEditorFreeplayState extends MusicBeatState
|
||||
{
|
||||
var weekFile:WeekFile = null;
|
||||
public function new(weekFile:WeekFile = null)
|
||||
{
|
||||
super();
|
||||
this.weekFile = WeekData.createWeekFile();
|
||||
if(weekFile != null) this.weekFile = weekFile;
|
||||
}
|
||||
|
||||
var bg:FlxSprite;
|
||||
private var grpSongs:FlxTypedGroup<Alphabet>;
|
||||
private var iconArray:Array<HealthIcon> = [];
|
||||
|
||||
var curSelected = 0;
|
||||
|
||||
override function create() {
|
||||
bg = new FlxSprite().loadGraphic(Paths.image('menuDesat'));
|
||||
bg.antialiasing = ClientPrefs.globalAntialiasing;
|
||||
|
||||
bg.color = FlxColor.WHITE;
|
||||
add(bg);
|
||||
|
||||
grpSongs = new FlxTypedGroup<Alphabet>();
|
||||
add(grpSongs);
|
||||
|
||||
for (i in 0...weekFile.songs.length)
|
||||
{
|
||||
var songText:Alphabet = new Alphabet(0, (70 * i) + 30, weekFile.songs[i][0], true, false);
|
||||
songText.isMenuItem = true;
|
||||
songText.targetY = i;
|
||||
grpSongs.add(songText);
|
||||
|
||||
var icon:HealthIcon = new HealthIcon(weekFile.songs[i][1]);
|
||||
icon.sprTracker = songText;
|
||||
|
||||
// using a FlxGroup is too much fuss!
|
||||
iconArray.push(icon);
|
||||
add(icon);
|
||||
|
||||
// songText.x += 40;
|
||||
// DONT PUT X IN THE FIRST PARAMETER OF new ALPHABET() !!
|
||||
// songText.screenCenter(X);
|
||||
}
|
||||
|
||||
addEditorBox();
|
||||
changeSelection();
|
||||
super.create();
|
||||
}
|
||||
|
||||
var UI_box:FlxUITabMenu;
|
||||
var blockPressWhileTypingOn:Array<FlxUIInputText> = [];
|
||||
function addEditorBox() {
|
||||
var tabs = [
|
||||
{name: 'Freeplay', label: 'Freeplay'},
|
||||
];
|
||||
UI_box = new FlxUITabMenu(null, tabs, true);
|
||||
UI_box.resize(250, 200);
|
||||
UI_box.x = FlxG.width - UI_box.width - 100;
|
||||
UI_box.y = FlxG.height - UI_box.height - 60;
|
||||
UI_box.scrollFactor.set();
|
||||
|
||||
UI_box.selected_tab_id = 'Week';
|
||||
addFreeplayUI();
|
||||
add(UI_box);
|
||||
|
||||
var blackBlack:FlxSprite = new FlxSprite(0, 670).makeGraphic(FlxG.width, 50, FlxColor.BLACK);
|
||||
blackBlack.alpha = 0.6;
|
||||
add(blackBlack);
|
||||
|
||||
var loadWeekButton:FlxButton = new FlxButton(0, 685, "Load Week", function() {
|
||||
WeekEditorState.loadWeek();
|
||||
});
|
||||
loadWeekButton.screenCenter(X);
|
||||
loadWeekButton.x -= 120;
|
||||
add(loadWeekButton);
|
||||
|
||||
var storyModeButton:FlxButton = new FlxButton(0, 685, "Story Mode", function() {
|
||||
MusicBeatState.switchState(new WeekEditorState(weekFile));
|
||||
|
||||
});
|
||||
storyModeButton.screenCenter(X);
|
||||
add(storyModeButton);
|
||||
|
||||
var saveWeekButton:FlxButton = new FlxButton(0, 685, "Save Week", function() {
|
||||
WeekEditorState.saveWeek(weekFile);
|
||||
});
|
||||
saveWeekButton.screenCenter(X);
|
||||
saveWeekButton.x += 120;
|
||||
add(saveWeekButton);
|
||||
}
|
||||
|
||||
override function getEvent(id:String, sender:Dynamic, data:Dynamic, ?params:Array<Dynamic>) {
|
||||
if(id == FlxUIInputText.CHANGE_EVENT && (sender is FlxUIInputText)) {
|
||||
weekFile.songs[curSelected][1] = iconInputText.text;
|
||||
iconArray[curSelected].changeIcon(iconInputText.text);
|
||||
} else if(id == FlxUINumericStepper.CHANGE_EVENT && (sender is FlxUINumericStepper)) {
|
||||
if(sender == bgColorStepperR || sender == bgColorStepperG || sender == bgColorStepperB) {
|
||||
updateBG();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var bgColorStepperR:FlxUINumericStepper;
|
||||
var bgColorStepperG:FlxUINumericStepper;
|
||||
var bgColorStepperB:FlxUINumericStepper;
|
||||
var iconInputText:FlxUIInputText;
|
||||
function addFreeplayUI() {
|
||||
var tab_group = new FlxUI(null, UI_box);
|
||||
tab_group.name = "Freeplay";
|
||||
|
||||
bgColorStepperR = new FlxUINumericStepper(10, 40, 20, 255, 0, 255, 0);
|
||||
bgColorStepperG = new FlxUINumericStepper(80, 40, 20, 255, 0, 255, 0);
|
||||
bgColorStepperB = new FlxUINumericStepper(150, 40, 20, 255, 0, 255, 0);
|
||||
|
||||
var copyColor:FlxButton = new FlxButton(10, bgColorStepperR.y + 25, "Copy Color", function() {
|
||||
Clipboard.text = bg.color.red + ',' + bg.color.green + ',' + bg.color.blue;
|
||||
});
|
||||
var pasteColor:FlxButton = new FlxButton(140, copyColor.y, "Paste Color", function() {
|
||||
if(Clipboard.text != null) {
|
||||
var leColor:Array<Int> = [];
|
||||
var splitted:Array<String> = Clipboard.text.trim().split(',');
|
||||
for (i in 0...splitted.length) {
|
||||
var toPush:Int = Std.parseInt(splitted[i]);
|
||||
if(!Math.isNaN(toPush)) {
|
||||
if(toPush > 255) toPush = 255;
|
||||
else if(toPush < 0) toPush *= -1;
|
||||
leColor.push(toPush);
|
||||
}
|
||||
}
|
||||
|
||||
if(leColor.length > 2) {
|
||||
bgColorStepperR.value = leColor[0];
|
||||
bgColorStepperG.value = leColor[1];
|
||||
bgColorStepperB.value = leColor[2];
|
||||
updateBG();
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
iconInputText = new FlxUIInputText(10, bgColorStepperR.y + 70, 100, '', 8);
|
||||
|
||||
var hideFreeplayCheckbox:FlxUICheckBox = new FlxUICheckBox(10, iconInputText.y + 30, null, null, "Hide Week from Freeplay?", 100);
|
||||
hideFreeplayCheckbox.checked = weekFile.hideFreeplay;
|
||||
hideFreeplayCheckbox.callback = function()
|
||||
{
|
||||
weekFile.hideFreeplay = hideFreeplayCheckbox.checked;
|
||||
};
|
||||
|
||||
tab_group.add(new FlxText(10, bgColorStepperR.y - 18, 0, 'Selected background Color R/G/B:'));
|
||||
tab_group.add(new FlxText(10, iconInputText.y - 18, 0, 'Selected icon:'));
|
||||
tab_group.add(bgColorStepperR);
|
||||
tab_group.add(bgColorStepperG);
|
||||
tab_group.add(bgColorStepperB);
|
||||
tab_group.add(copyColor);
|
||||
tab_group.add(pasteColor);
|
||||
tab_group.add(iconInputText);
|
||||
tab_group.add(hideFreeplayCheckbox);
|
||||
UI_box.addGroup(tab_group);
|
||||
}
|
||||
|
||||
function updateBG() {
|
||||
weekFile.songs[curSelected][2][0] = Math.round(bgColorStepperR.value);
|
||||
weekFile.songs[curSelected][2][1] = Math.round(bgColorStepperG.value);
|
||||
weekFile.songs[curSelected][2][2] = Math.round(bgColorStepperB.value);
|
||||
bg.color = FlxColor.fromRGB(weekFile.songs[curSelected][2][0], weekFile.songs[curSelected][2][1], weekFile.songs[curSelected][2][2]);
|
||||
}
|
||||
|
||||
function changeSelection(change:Int = 0) {
|
||||
FlxG.sound.play(Paths.sound('scrollMenu'), 0.4);
|
||||
|
||||
curSelected += change;
|
||||
|
||||
if (curSelected < 0)
|
||||
curSelected = weekFile.songs.length - 1;
|
||||
if (curSelected >= weekFile.songs.length)
|
||||
curSelected = 0;
|
||||
|
||||
var bullShit:Int = 0;
|
||||
for (i in 0...iconArray.length)
|
||||
{
|
||||
iconArray[i].alpha = 0.6;
|
||||
}
|
||||
|
||||
iconArray[curSelected].alpha = 1;
|
||||
|
||||
for (item in grpSongs.members)
|
||||
{
|
||||
item.targetY = bullShit - curSelected;
|
||||
bullShit++;
|
||||
|
||||
item.alpha = 0.6;
|
||||
// item.setGraphicSize(Std.int(item.width * 0.8));
|
||||
|
||||
if (item.targetY == 0)
|
||||
{
|
||||
item.alpha = 1;
|
||||
// item.setGraphicSize(Std.int(item.width));
|
||||
}
|
||||
}
|
||||
trace(weekFile.songs[curSelected]);
|
||||
iconInputText.text = weekFile.songs[curSelected][1];
|
||||
bgColorStepperR.value = Math.round(weekFile.songs[curSelected][2][0]);
|
||||
bgColorStepperG.value = Math.round(weekFile.songs[curSelected][2][1]);
|
||||
bgColorStepperB.value = Math.round(weekFile.songs[curSelected][2][2]);
|
||||
updateBG();
|
||||
}
|
||||
|
||||
override function update(elapsed:Float) {
|
||||
if(WeekEditorState.loadedWeek != null) {
|
||||
super.update(elapsed);
|
||||
FlxTransitionableState.skipNextTransIn = true;
|
||||
FlxTransitionableState.skipNextTransOut = true;
|
||||
MusicBeatState.switchState(new WeekEditorFreeplayState(WeekEditorState.loadedWeek));
|
||||
WeekEditorState.loadedWeek = null;
|
||||
return;
|
||||
}
|
||||
|
||||
if(iconInputText.hasFocus) {
|
||||
FlxG.sound.muteKeys = [];
|
||||
FlxG.sound.volumeDownKeys = [];
|
||||
FlxG.sound.volumeUpKeys = [];
|
||||
if(FlxG.keys.justPressed.ENTER) {
|
||||
iconInputText.hasFocus = false;
|
||||
}
|
||||
} else {
|
||||
FlxG.sound.muteKeys = TitleState.muteKeys;
|
||||
FlxG.sound.volumeDownKeys = TitleState.volumeDownKeys;
|
||||
FlxG.sound.volumeUpKeys = TitleState.volumeUpKeys;
|
||||
if(FlxG.keys.justPressed.ESCAPE) {
|
||||
FlxG.mouse.visible = false;
|
||||
MusicBeatState.switchState(new editors.MasterEditorMenu());
|
||||
FlxG.sound.playMusic(Paths.music('freakyMenu'));
|
||||
}
|
||||
|
||||
if(controls.UI_UP_P) changeSelection(-1);
|
||||
if(controls.UI_DOWN_P) changeSelection(1);
|
||||
}
|
||||
super.update(elapsed);
|
||||
}
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue