import { logger } from "../logger.js" ; import { Arithmetic , ArithmeticOperations } from "../entities/Arithmetic.js" ; import { Color , Endpoint , Entity , makeConnection , signalC , signalV } from "../entities/Entity.js" ; import { MergeEl } from "./MergeNode.js" ; export type nodeFunc = ( n : ( number | string ) [ ] ) => Node ; export type mergeFunc = ( n : ( number | string ) [ ] ) => MergeEl [ ] ; export function createTransformer ( input ? , sig = signalC ) { let trans = new Arithmetic ( { first_signal : signalV , second_constant : 0 , operation : ArithmeticOperations . Or , output_signal : sig } ) ; if ( input ) makeConnection ( Color . Red , input , trans . input ) ; return trans ; } export function createLimiter ( mask ) { if ( mask == - 1 ) { return new Arithmetic ( { first_signal : signalV , second_constant : 0 , operation : ArithmeticOperations . Or , output_signal : signalV } ) ; } else { return new Arithmetic ( { first_signal : signalV , second_constant : mask , operation : ArithmeticOperations . And , output_signal : signalV } ) ; } } export abstract class Node { outputBits : number [ ] ; outMask : number ; outputPlaceholder : Endpoint ; constructor ( bits ) { logger . assert ( bits . length <= 32 , `Wire width too big: ${ bits . length }` ) ; this . outputBits = bits ; this . outMask = bits . length == 32 ? - 1 : ( ( ( 1 << bits . length ) - 1 ) | 0 ) ; this . outputPlaceholder = new Endpoint ( null , - 1 ) ; } public connect ( getInputNode , getMergeEls ) { let e = this . _connect ( getInputNode , getMergeEls ) ; if ( ! e ) { if ( this . outputPlaceholder . red || this . outputPlaceholder . green ) throw new Error ( "missing output endpoint" ) ; this . outputPlaceholder = null ; } else { this . _setOutput ( e ) ; } } abstract _connect ( getInputNode , getMergeEls ) ; protected _setOutput ( e ) { if ( this . outputPlaceholder . red ) { makeConnection ( Color . Red , e , this . outputPlaceholder ) ; this . outputPlaceholder . red . remove ( this . outputPlaceholder ) ; } if ( this . outputPlaceholder . green ) { makeConnection ( Color . Green , e , this . outputPlaceholder ) ; this . outputPlaceholder . green . remove ( this . outputPlaceholder ) ; } this . outputPlaceholder = e ; } public output ( ) { return this . outputPlaceholder ; } abstract combs ( ) ; }