TypeScript - Some Helpful Functions for Construct

1 favourites
  • 1 posts
From the Asset Store
Casino? money? who knows? but the target is the same!
  • Hey all,

    While doing my first big typescript project I've posted a couple of times about random issues I have found

    I thought this time I would give back with some useful functions that I have found/written along the way!

    Most of these were found during the conversion from raw Javascript to Typescript, as by default TS doesn't let you do the weird-hacks that JS does

    Since when has that stopped anyone however!

    I will add to this thread when I find more weird things to do, the project I have building for this can be found on Github Here if anyone is interested!

    Please enjoy, and run at your own risk!

    Get Construct Object Type from String

    Example Usage => Get the specific Bullet you want your Turret to spawn, when the turret baseline are Family based

    // general typescript function, to get the property off the object using 
    export function getProperty<T, K extends keyof T>(o: T, propertyName: K): T[K] {
     return o[propertyName]; // o[propertyName] is of type T[K]
    }
    
    // get an ObjectType from the runtime objects list based on the name of the object
    // mostly used to be able to spawn items via configuration
    export function getObjectType<T extends IWorldInstance>(runtime: IRuntime, name: string): IObjectType<T> {
     // get the object key using the Construct Object Name
     // eg - runtime.objects.MyEnemyType
     const typekey = name as keyof IConstructProjectObjects;
     return getProperty(runtime.objects, typekey) as IObjectType<T>;
    }

    Get Effect Type - Bug Workaround

    Currently accessing Effects via typescript is bugged - discussed here

    // bugfix workaround for effects
    // casts the effects object to an array, then pulls the type via name
    export function getEffectType(effectArray: any , name: string): IEffectInstance | null {
     const hackCast = effectArray as IEffectInstance[];
     const found = hackCast.find((ef) => ef.name == name);
     return found != null ? found as IEffectInstance : null;
    }
    

    Parse a Project JSON File at runtime

    export const safeJsonParse = <T>(str: string) => {
     try {
     const jsonValue: T = JSON.parse(str);
    
     return jsonValue;
     } catch {
     return undefined;
     }
    };
    export const safeGetConstructFileJson = <T>(runtime: IRuntime, fileName: string) : Promise<T> =>{
    	return new Promise((resolve, reject) =>
     runtime.assets
     // get project file URL Promise
     .getProjectFileUrl(fileName)
     .then((filepath) =>
     // ajax get the file contents (also promise)
     fetch(filepath)
     .then((response) =>
     // get the text from the file (AGAIN another promis)
     response.text()
     .then((rawJSON) => {
     // parse the results
     const result = safeJsonParse<T>(rawJSON);
     result !== undefined
     // funally resolve the promise stack
     ? resolve(result)
     : reject(`Unable to parse to ${fileName} : + ${rawJSON}`);
     })
     .catch((reason) => reject(`Unable to fetch ${fileName} Datafile - ${reason}`))
     )
     .catch((reason) => `Unable to FIND ${fileName} data file - ${reason}`)
     )
     .catch((reason) => `the install didnt work, cant find ${fileName} - ${reason}`)
     );
    }
    
    

    Easy Instance Object Configuration

    runtime.objects.Type.setInstanceClass

    Doing that manually is very boring and very prone to human error

    So I made a method to do it easy

    async function ConfigureCustomTypes(runtime:IRuntime)
    {
    	const customTypeMapping = [
     {
     InstanceType: EnemyControl,
     ConstructObjectTypes: [runtime.objects.BasicEnemy, runtime.objects.BasicEnemy2],
     },
     {
     InstanceType: TowerController,
     ConstructObjectTypes: [runtime.objects.basicTower, runtime.objects.BasicTower2],
     },
    	...
    ];
    	customTypeMapping.forEach(tm => {
    		const type = tm.InstanceType;
    		tm.ConstructObjectTypes.forEach((n) => {
     if (n != null) n.setInstanceClass(type);
     });
    	})
    
    

    Make 2D Array

    Want to make a giant 2d array to represent say a grid?

    Say to map objects on top of a tile map?

    function makeArray<T>(w: number, h: number, val: T) {
     var arr: T[][] = [];
     for(let i = 0; i < w; i++) {
     arr[i] = [];
     for(let j = 0; j < h; j++) {
     arr[i][j] = val;
     }
     }
     return arr;
    }

    Get Tilemap Coords from Mouseclick

    You have a tilemap

    you have things ONTOP of the tile map, and you need to figure out if there is something IN the tilemap

    	// do this earlier somewhere to use
     mouseXYAr = this.gridLayer!.cssPxToLayer(pointerEvent.clientX, pointerEvent.clientY);
    
    
     private getGridCoordsAndSize(tilemap: ITilemapInstance, mouseXYAr: number[]) {
     const tileSizeX = tilemap.tileWidth;
     const tileSizeY = tilemap.tileHeight;
    
     const cellCoords = [Math.floor(mouseXYAr[0] / tileSizeX), Math.floor(mouseXYAr[1] / tileSizeY)];
     return { cellCoords, tileSizeX, tileSizeY };
     }
    
  • Try Construct 3

    Develop games in your browser. Powerful, performant & highly capable.

    Try Now Construct 3 users don't see these ads
Jump to:
Active Users
There are 3 visitors browsing this topic (0 users and 3 guests)