Watch-Game.ps1
function Watch-Game { <# .Synopsis Watches the Game Loop .Description While the game is running, this function will: * Watch for keyboard input * Call any key handlers * Call any OnTick events found on the Game, CurrentLevel, or loaded sprites * Sleep until the next expected $game.Clock event .Notes Unless you are building a game, you won't run this command directly. This command will be run within Initialize-Game, which in turn is called .Example Initialize-Game -GamePath .\ROM\Nibbles2020 | Add-Member NoteProperty IsRunning $true -Force -PassThru | Watch-Game .Link Start-Game .Link Initialize-Game #> param( # The Game Object [Parameter(Mandatory,Position=0,ValueFromPipeline,ValueFromPipelineByPropertyName,ParameterSetName='Game')] [Parameter(Position=1,ParameterSetName='LevelPath')] [PSObject] $Game ) begin { $NotifyTick = { if ($game.OnTick.Invoke) { $game.OnTick() } if ($game.CurrentLevel.OnTick.Invoke) { $game.CurrentLevel.OnTick() } foreach ($gameSprite in @($game.CurrentLevel.Sprites)) { if ($gameSprite.OnTick.Invoke) { $gameSprite.OnTick() } } } } process { $lastTick = $null $game | Add-Member NoteProperty LoopCounter 0 -Force :GameLoop while ($game.IsRunning) { $game.LoopCounter++ & $NotifyTick $keyInput = @( $keySplat = @{} if ($Game.KeyHandlers) { $keySplat['OnKey'] = $Game.KeyHandlers } . Watch-Keyboard @keySplat ) if ($keyInput -and $keyInput.Key.VirtualKeyCode -ne 10 -and $keyInput.Key.VirtualKeyCode -ne 13) { $null = $null } $gameClock = $game.Clock -as [Timespan] if (-not $gameClock) { $gameClock = [Timespan]'00:00:00.02' } do { [Threading.Thread]::Sleep(1) # Start-Sleep -Milliseconds 1 } while ($lastTick -and ([DateTime]::Now -lt $nextTick)) $lastTick = [DateTime]::Now $nextTick = $lastTick + $gameClock } } } |