Skip to content

Commit

Permalink
WIP new wild plan!
Browse files Browse the repository at this point in the history
  • Loading branch information
hubol committed Sep 4, 2024
1 parent 5152a04 commit 9bd69a2
Show file tree
Hide file tree
Showing 5 changed files with 141 additions and 11 deletions.
121 changes: 114 additions & 7 deletions esbuild.prommy.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import ts from 'typescript';
// ($prommyResult = await sleep(32), $prommyPop(), $prommyResult)

const Consts = {
ContextParameterName: '$c',
PopFunctionName: '$prommyPop',
ResultIdentifier: '$prommyResult',
PrommyType: 'Prommy',
Expand Down Expand Up @@ -108,6 +109,97 @@ function isPrommyOrPromiseOfPrommy(type) {
return false;
}

/**
*
* @param {import("typescript").Node} node
*/
function isFunctionDeclarationReturningPromise(node) {
if (ts.isFunctionDeclaration(node) || ts.isArrowFunction(node)) {
const type = Ts.checker.getTypeAtLocation(node);
for (const signature of type.getCallSignatures()) {
if (signature.resolvedReturnType.symbol?.name === 'Promise') {
return true;
}
}
}

return false;
}

/**
*
* @param {import("typescript").Node} node
*/
function oneSignatureHasContextParameter(node) {
const type = Ts.checker.getTypeAtLocation(node);
return type.callSignatures.some(signature => signature.parameters.some(parameter => parameter.name === Consts.ContextParameterName));
}

/**
* @param {import("typescript").NodeFactory} factory
* @param {import("typescript").Node} node
*/
function createFunctionDeclarationWithContextParameter(factory, node) {
if (ts.isFunctionDeclaration(node)) {
return factory.createFunctionDeclaration(
node.modifiers,
node.asteriskToken,
node.name,
node.typeParameters,
[ ...node.parameters, factory.createParameterDeclaration(undefined, undefined, '$c') ],
node.type,
node.body);
}

return factory.createArrowFunction(
node.modifiers,
node.typeParameters,
[ ...node.parameters, factory.createParameterDeclaration(undefined, undefined, '$c') ],
node.type,
node.equalsGreaterThanToken,
node.body,
)
}

const results = {
callChains: [],
callExpressions: [],
callLikeExpressions: [],
callOrNewExpressions: [],
}

const promiseMethods = new Set([ 'then', 'catch', 'finally' ]);

/**
*
* @param {import("typescript").Node} node
*/
function isInvocationOfFunctionThatReturnsPromise(node) {
if (ts.isCallExpression(node)) {
const expressionSymbol = Ts.checker.getTypeAtLocation(node.expression).symbol;

if (promiseMethods.has(expressionSymbol?.name))
return false;
if (expressionSymbol?.parent?.name === 'PromiseConstructor')
return false;
if (Ts.checker.getTypeAtLocation(node).symbol?.name === 'Promise')
return true;
}

return false;
}

/**
* @param {import("typescript").NodeFactory} factory
* @param {import("typescript").CallExpression} node
*/
function createCallExpressionWithContextParameter(factory, node) {
return factory.createCallExpression(
node.expression,
node.typeArguments,
[ ...node.arguments, factory.createIdentifier(Consts.ContextParameterName) ]);
}

/**
*
* @param {import("typescript").TransformationContext} context
Expand All @@ -116,19 +208,32 @@ function isPrommyOrPromiseOfPrommy(type) {
const transformSourceFile = (context) => (sourceFile) => {
const { factory } = context;

// A visitor function to traverse the AST
/**
*
* @param {import("typescript").Node} node
*/
function visitor(node) {
if (isInvocationOfFunctionThatReturnsPromise(node)) {
return ts.visitEachChild(createCallExpressionWithContextParameter(factory, node), visitor, context);
}

if (isFunctionDeclarationReturningPromise(node)) {
const acceptsContextArgument = oneSignatureHasContextParameter(node);
if (!acceptsContextArgument)
return ts.visitEachChild(createFunctionDeclarationWithContextParameter(factory, node), visitor, context);
}

if (ts.isAwaitExpression(node)) {
const expression = node.expression;
const type = Ts.checker.getTypeAtLocation(expression);

if (type.symbol?.name === 'Promise') {
return createPoppingAwaitExpressionOfWrappedPrommy(factory, node);
}
// if (type.symbol?.name === 'Promise') {
// return ts.visitEachChild(createPoppingAwaitExpressionOfWrappedPrommy(factory, node), visitor, context);
// }

if (isPrommyOrPromiseOfPrommy(type)) {
return createPoppingAwaitExpression(factory, node);
}
// if (isPrommyOrPromiseOfPrommy(type)) {
// return createPoppingAwaitExpression(factory, node);
// }
}
return ts.visitEachChild(node, visitor, context);
}
Expand Down Expand Up @@ -168,6 +273,8 @@ export function transformFile(fileName) {

const newSourceText = Ts.printer.printFile(result.transformed[0]);
transformedTextCache.set(fileName, newSourceText);

return newSourceText;
}

export function initializeTs() {
Expand Down
8 changes: 8 additions & 0 deletions prommy-test.mjs
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
import { initializeTs, transformFile } from './esbuild.prommy.mjs'

initializeTs();

// transformFile('C:/Users/hubol/Projects/igua-rpg2/src/igua/objects/obj-test.ts')
console.log(transformFile('C:/Users/hubol/Projects/igua-rpg2/src/igua/objects/obj-test.ts'))
// console.log(transformFile('C:/Users/hubol/Projects/igua-rpg2/src/igua/ui/iguana-designer/obj-ui-iguana-designer-root.ts'))
process.exit(0);
16 changes: 16 additions & 0 deletions src/igua/objects/obj-test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
import { wait } from "../../lib/game-engine/promise/wait";
import { container } from "../../lib/pixi/container";

async function myAsyncFunction() {

}

export function objTest() {
return container()
.async(async () => {
await wait(() => true);
await myAsyncFunction();
await myAsyncFunction().then(myAsyncFunction);
await Promise.all([myAsyncFunction()]);
})
}
2 changes: 1 addition & 1 deletion src/igua/ui/iguana-designer/obj-ui-iguana-designer-root.ts
Original file line number Diff line number Diff line change
Expand Up @@ -310,7 +310,7 @@ function objIguanaPreview(minX = 102, maxX = 253) {
if (bigPuppet.gait > 0)
bigPuppet.pedometer += 0.1;
})
.async(async () => {
.async(async ($c) => {
while (true) {
await sleep(1000);
await lerp(bigPuppet, 'ducking').to(1).over(300);
Expand Down
5 changes: 2 additions & 3 deletions src/lib/game-engine/promise/wait.ts
Original file line number Diff line number Diff line change
@@ -1,16 +1,15 @@
import { AsshatMicrotaskFactory } from "./asshat-microtasks";
import { AsshatZone } from "../asshat-zone";
import { Prommy } from "../../zone/prommy";

type Predicate = () => boolean;

export function wait(predicate: Predicate) {
if (predicate())
return Prommy.resolve();
return Promise.resolve();

const context = AsshatZone.context;

return new Prommy<void>((resolve, reject) => {
return new Promise<void>((resolve, reject) => {
const microtask = AsshatMicrotaskFactory.create(predicate, context, resolve, reject);
context.ticker.addMicrotask(microtask);
});
Expand Down

0 comments on commit 9bd69a2

Please sign in to comment.