Haxe 4.1.5 save data? - haxe

I've been modding Friday Night Funkin' lately, and I've been wanting to work on save files. I've tried to use FlxSave, but that hasn't worked. Directly changing the FlxG.save.data values didn't work either. I'm using Haxe 4.1.5. Am I doing something wrong, or is it just a bug? Here's my code for saving:
import flixel.FlxSubState;
import flixel.FlxG;
import flixel.FlxSprite;
import flixel.util.FlxSave;
import flixel.group.FlxGroup.FlxTypedGroup;
import flixel.text.FlxText;
import flixel.util.FlxColor;
public function new()
{
//super();
super();
//lots of this was cut soo
FlxG.save.bind('funkin', 'dark279');
case "Offset":
offset --;
FlxG.save.data.offset = offset;
FlxG.save.flush();
}
}
case "Offset":
offset ++;
FlxG.save.data.offset = offset;
FlxG.save.flush();
}
}
if (controls.BACK)
{
FlxG.save.flush();
//switch state
Much shorter than the full thing, but all of the saving code is there.

I really forgot to set offset to the saved offset.. omg I'm so dumb

Related

Splitting inversifyJS config file into multiple files

I recently bumped into a backend project using Typescript and would like to implement IoC principle with the help of Inversify.js. Following the official documentation, I have one huge file named inversify.config.ts containing all my interfaces and classes that implement them:
import "reflect-metadata"
import { Container } from "inversify"
import TYPES from './types';
import { ModuleRepo } from '../repo/interfaces'
import { ModuleARepoImpl } from '../repo/moduleA'
import { ModuleBRepoImpl } from '../repo/moduleB'
import { ModuleService } from '../services/interfaces'
import { ModuleAServiceImpl } from '../services/moduleA'
import { ModuleBServiceImpl } from '../services/moduleB'
const container = Container();
container.bind<ModuleRepo>(TYPES.ModuleARepo).to(ModuleARepoImpl);
container.bind<ModuleRepo>(TYPES.ModuleBRepo).to(ModuleBRepoImpl);
container.bind<ModuleService>(TYPES.ModuleAService).to(ModuleAServiceImpl);
container.bind<ModuleService>(TYPES.ModuleBService).to(ModuleBServiceImpl);
export default container;
One big problem in the above setting is when the project gets complex, more modules are added resulting in a very long config file (imagine you have dozens of modules). My plan is to divide it into smaller config files, with inversify.config.ts remains the main file.
consider the following settings:
./dependencies/interface/index.ts
import { Container } from 'inversify';
export type InversifyContainer = Container
export interface BasicInterface {
register(container: InversifyContainer): void
readonly types: Object
}
./dependencies/moduleA/index.ts
import {InversifyContainer, BasicDependencies} from '../interface';
import { ModuleRepo } from '../../repo/interfaces'
import { ModuleARepoImpl } from '../../repo/moduleA'
import { ModuleService } from '../../services/interfaces'
import { ModuleAServiceImpl } from '../../services/moduleA'
export class ModuleADependencies {
register(container: InversifyContainer) {
container.bind<ModuleRepo>(TYPES.ModuleARepo).to(ModuleARepoImpl);
container.bind<ModuleService>(TYPES.ModuleAService).to(ModuleAServiceImpl);
}
readonly types = {
ModuleARepo: Symbol('ModuleARepo'),
ModuleAService: Symbol('ModuleAService'),
}
}
./dependencies/inversify.config.ts
import "reflect-metadata"
import { Container } from "inversify"
import { ModuleADependencies } from './moduleA';
import { ModuleBDependencies } from './moduleB'; // consider moduleB also has the same file
const container = Container();
const registrationList = [ModuleADependencies, ModuleBDependencies];
for (const reg of registrationList) {
new reg().register(container);
}
export default container;
./dependencies/types.ts
import { ModuleADependencies } from './moduleA';
import { ModuleBDependencies } from './moduleB';
const TYPES = {
...(new ModuleADependencies().types),
...(new ModuleBDependencies().types),
}
export default TYPES
However, this way I always have an error showing something like Cannot read property of ModuleARepo of undefined from the types. I browsed the internet however nobody seems to care about how lengthy and messy inversify.config.ts would be if it is in a complex project.
Hoping someone can help with this :)
First of all your problem is described in the doc and has a solution.
Your solution is generally correct but there is a circular dependency
./dependencies/types.ts -> ./dependencies/moduleA/index.ts -> ./dependencies/types.ts
In types a new instance of class is created but the module that contain the class definition imports types. You don't list this import but use TYPES.ModuleARepo in bind.
To avoid it you can make types field static or move it out of the class into a separate exportable object. As a positive side effect of it, there will be no need to instantiate a class in ./dependencies/types.ts.
Just in case please keep in mind that if you instantiate a class that has a Symbol as a field this symbol is unique for every instance since Symbol('ModuleARepo') !== Symbol('ModuleARepo').
Playground

Is there a way to abstract the import from a node module using typescript config files in the same style as the 'paths' property?

I am creating private node modules which for now might change considerably in structure which could mean splitting existing code into multiple packages.
If I have 100 files importing from a package that no longer holds the import I can do a find and replace but it becomes more difficult when classes are imported from that package...
so something like:
import { thing1, thing2} from 'my-package';
in the future may need to be:
import { thing1} from 'my-package';
import { thing2} from 'my-package2';
You can abstract imports using tsconfig like so:
"paths": {
"#shared/*": ["app/shared/*"]
}
But I cant figure out a way to do the same thing with node modules so that if there is a bigger change I only need to change 1 line. Is this possible?
Create index.ts file , import and export your modules:
import { assign, assignWith } from 'lodash';
import { addDays } from 'date-fns';
export { assign, assignWith, addDays };
and import modules from that index:
import { assign, addDays } from './index';
Check https://github.com/nrwl/nx
They can help you in using monorepo approach.
You can split your system into Applications and Libraries.

Dagger2 ApplicationComponent not generated(git project included)

So I'm trying to follow Googles architecture example and my daggerappcomponent is not generating. I tried changing up the gradle files but I'm not sure what I'm doing wrong. First time doing something "advanced" like this(for me at least). I commented out everything from the DI package as I cannot get it working without the QuoteApplication, and I cant get QuoteApplication working without building the project and hoping it will generate necessary dagger files.
override fun applicationInjector(): AndroidInjector<out DaggerApplication> {
return DaggerApplicationComponent.factory().create(applicationContext) //here is the problem
}
Here's the project https://github.com/Nikola-Milovic/QuoteAppMvvm
I tried a lot of different build gradles and I tried cleaning rebuidling and so on. I've read all of the online fixes but nothing has worked. I'm certain it's my fault but it might be a bug or something. My last resort is to ask here. Kinda stuck at this.
It worked perfeclty fine for me.
I build.
The component is generated.
The buld fails because no import.
I import the newly created component. (import com.example.quoteappmvvm.di.DaggerApplicationComponent)
It works.
package com.example.quoteappmvvm
import com.example.quoteappmvvm.di.DaggerApplicationComponent >>>> You need this!!!
import dagger.android.AndroidInjector
import dagger.android.support.DaggerApplication
//open class QuoteApplication{
//// override fun applicationInjector(): AndroidInjector<out DaggerApplication> {
////
//// return DaggerApplicationComponent.factory().create(applicationContext)
//// }
//
//// override fun onCreate() {
//// super.onCreate()
//// // if (BuildConfig.DEBUG) Timber.plant(DebugTree())
//// }
//}
open class QuoteApplication : DaggerApplication() {
override fun applicationInjector(): AndroidInjector<out DaggerApplication> {
return DaggerApplicationComponent.factory().create(this)
}
override fun onCreate() {
super.onCreate()
// if (BuildConfig.DEBUG) Timber.plant(DebugTree())
}
}

Static data initialised twice due to typo in import in TypeScript

I have a newbie question on TypeScript imports. I tried to make a class which holds some data in a static variable, and the data is lazily initialised in getInstance() method.
myStaticClass.ts:
class MyData {
x = 1;
}
export class MyStaticClass {
private static data: MyData;
static getInstance() {
if (MyStaticClass.data == null) {
console.log('data is null, initialising');
MyStaticClass.data = new MyData();
}
return MyStaticClass.data;
}
}
I imported this class in 2 other classes:
a.ts
import { MyStaticClass } from './MyStaticClass';
// NOTE the typo above - uppercase file name
export class A {
logX() {
console.log(MyStaticClass.getInstance().x);
}
}
index.ts
import { MyStaticClass } from './myStaticClass';
import { A } from './a';
console.log(MyStaticClass.getInstance().x);
new A().logX();
To my surprise, the output of ts-node index.ts is
data is null, initialising
1
data is null, initialising
1
If I correct the import the output is as expected - data is initialised only once.
I also checked that I get one initialisation for one variant of spelling (added 3rd class with another letter in upperCase)
Can anyone explain why this behaviour is in place?
(Additionally, what tools / debug statements I could have used to identify what is happening?)
Can I force TypeScript to flag this as error?
I am on MacOs, TS 3.6.3, node-ts 8.4.1
While on Windows two differently cased file names always point to the same file, on other platforms they do not. This means that imports with different file names are treated as different modules, this is by design and is not considered an issue (see here for node discussion)
The simple solution is to force consistent file casing to be used when importing modules. Typescript does have a compiler option to force this named forceConsistentCasingInFileNames (See docs). This option should prevent such issues.

Custom update listener to set subtask's fix-version

I'm developing custom listener which will update subtask's fix version to same value as it's parent issue.
Currently we are using post-function in workflow in order to set subtask's fix version according to parent on subtask creation. This however doesn't cover cases when subtask already exists and parent's fix version gets updated. New value from parent task is not propagated to subtask.
I'm using script runner and I'm creating 'Custom lisatener', for my specific project and specified Event: 'Issue Updated'. I added script as following:
import com.atlassian.jira.component.ComponentAccessor
import com.atlassian.jira.config.SubTaskManager
import com.atlassian.jira.event.issue.AbstractIssueEventListener
import com.atlassian.jira.event.issue.IssueEvent
import com.atlassian.jira.event.type.EventDispatchOption
import com.atlassian.jira.issue.Issue
import com.atlassian.jira.issue.IssueManager
import com.atlassian.jira.issue.MutableIssue
import com.atlassian.jira.project.version.Version
import org.apache.log4j.Logger
class CopyFixVersionFromParentToChild extends AbstractIssueEventListener {
Logger log = Logger.getLogger(CopyFixVersionFromParentToChild.class);
SubTaskManager subTaskManager = ComponentAccessor.getComponent(SubTaskManager.class)
IssueManager issueManager = ComponentAccessor.getComponent(IssueManager.class)
#Override
void issueUpdated(IssueEvent event) {
log.warn("\nIssue updated!!!\n")
try {
Issue updatedIssue = event.getIssue()
if (updatedIssue.issueTypeObject.name == "Parent issue type") {
Collection<Version> fixVersions = new ArrayList<Version>()
fixVersions = updatedIssue.getFixVersions()
Collection<Issue> subTasks = updatedIssue.getSubTaskObjects()
if (subTaskManager.subTasksEnabled && !subTasks.empty) {
subTasks.each {
if (it instanceof MutableIssue) {
((MutableIssue) it).setFixVersions(fixVersions)
issueManager.updateIssue(event.getUser(), it, EventDispatchOption.ISSUE_UPDATED, false)
}
}
}
}
} catch (ex) {
log.debug "Event: ${event.getEventTypeId()} fired for ${event.issue} and caught by script 'CopyVersionFromParentToChild'"
log.debug(ex.getMessage())
}
}
}
Problem is, that it doesn't work. I'm not sure whethe rit's problem that my script logic is encapsulated inside class. Do I have to register this in some specific way? Or am I using script runner completely wrong and I'm pasting this script to wrong section? I checked code against JIRA API and it looks like it should work, my IDE doesnt show any warnings/errors.
Also, could anyone give me hints on where to find logging output from custom scripts like this? Whatever message I put into logger, I seem to be unable to find anywhere in JIRA logs (although I'm aware that script might not work for now).
Any response is much appreciated guys, Thanks.
Martin
Well, I figure it out.
Method I posted, which implements listener as groovy class is used in different way than I expected. These kind of script files were used to be located in to specific path in JIRA installation and ScriptRunner would register them into JIRA as listeners.
In in order to create 'simple' listener script which reacts to issue updated event, I had to strip it down to this code
import com.atlassian.jira.component.ComponentAccessor
import com.atlassian.jira.event.type.EventDispatchOption
import com.atlassian.jira.issue.Issue
import com.atlassian.jira.issue.IssueManager
import com.atlassian.jira.issue.MutableIssue
import com.atlassian.jira.project.version.Version
IssueManager issueManager = ComponentAccessor.getComponent(IssueManager.class)
Issue updatedIssue = event.getIssue()
Collection<Version> fixVersions = new ArrayList<Version>()
fixVersions = updatedIssue.getFixVersions()
Collection<Issue> subTasks = updatedIssue.getSubTaskObjects()
subTasks.each {
if (it instanceof MutableIssue) {
((MutableIssue) it).setFixVersions(fixVersions)
issueManager.updateIssue(event.getUser(), it, EventDispatchOption.ISSUE_UPDATED, false)
}
}
You past this to script runner interface and it works :-). Hope this helps anyone who's learning ScriptRunner. Cheers.
Matthew

Resources