示例#1
0
func (v *Video) Render() {
	for running {
		select {
		case dimensions := <-v.resize:
			v.ResizeEvent(dimensions[0], dimensions[1])
		case val := <-v.tick:
			slice := make([]uint8, len(val)*3)
			for i := 0; i < len(val); i = i + 1 {
				slice[i*3+0] = (uint8)((val[i] >> 16) & 0xff)
				slice[i*3+1] = (uint8)((val[i] >> 8) & 0xff)
				slice[i*3+2] = (uint8)((val[i]) & 0xff)
			}

			gl.Clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT)

			v.tex.Bind(gl.TEXTURE_2D)

			if ppu.OverscanEnabled {
				gl.TexImage2D(gl.TEXTURE_2D, 0, 3, 240, 224, 0, gl.RGB, gl.UNSIGNED_BYTE, slice)
			} else {
				gl.TexImage2D(gl.TEXTURE_2D, 0, 3, 256, 240, 0, gl.RGB, gl.UNSIGNED_BYTE, slice)
			}

			gl.TexParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST)
			gl.TexParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST)

			gl.Begin(gl.QUADS)
			gl.TexCoord2f(0.0, 1.0)
			gl.Vertex3f(-1.0, -1.0, 0.0)
			gl.TexCoord2f(1.0, 1.0)
			gl.Vertex3f(1.0, -1.0, 0.0)
			gl.TexCoord2f(1.0, 0.0)
			gl.Vertex3f(1.0, 1.0, 0.0)
			gl.TexCoord2f(0.0, 0.0)
			gl.Vertex3f(-1.0, 1.0, 0.0)
			gl.End()

			if v.screen != nil {
				sdl.GL_SwapBuffers()
			}

			v.frametick <- true
		}
	}
}
示例#2
0
func (v *Video) Render() {
	for running {
		select {
		case buf := <-v.videoTick:
			gl.Clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT)

			v.prog.Use()

			gl.ActiveTexture(gl.TEXTURE0)
			v.texture.Bind(gl.TEXTURE_2D)

			gl.TexImage2D(gl.TEXTURE_2D, 0, 3, 240, 224, 0, gl.RGBA,
				gl.UNSIGNED_INT_8_8_8_8, buf)

			gl.DrawArrays(gl.TRIANGLES, 0, 6)

			if v.screen != nil {
				sdl.GL_SwapBuffers()
				v.fpsmanager.FramerateDelay()
			}
		case ev := <-sdl.Events:
			switch e := ev.(type) {
			case sdl.ResizeEvent:
				v.ResizeEvent(int(e.W), int(e.H))
			case sdl.QuitEvent:
				os.Exit(0)
			case sdl.KeyboardEvent:
				switch e.Keysym.Sym {
				case sdl.K_ESCAPE:
					running = false
				case sdl.K_r:
					// Trigger reset interrupt
					if e.Type == sdl.KEYDOWN {
						// cpu.RequestInterrupt(InterruptReset)
					}
				case sdl.K_l:
					if e.Type == sdl.KEYDOWN {
						nes.LoadGameState()
					}
				case sdl.K_s:
					if e.Type == sdl.KEYDOWN {
						nes.SaveGameState()
					}
				case sdl.K_i:
					if e.Type == sdl.KEYDOWN {
						nes.AudioEnabled = !nes.AudioEnabled
					}
				case sdl.K_p:
					if e.Type == sdl.KEYDOWN {
						nes.TogglePause()
					}
				case sdl.K_d:
					if e.Type == sdl.KEYDOWN {
						jsHandler.ReloadFile(debugfile)
					}
				case sdl.K_m:
					if e.Type == sdl.KEYDOWN {
						nes.Handler.Handle("debug-mode")
					}
				case sdl.K_BACKSLASH:
					if e.Type == sdl.KEYDOWN {
						nes.Pause()
						nes.StepFrame()
					}
				case sdl.K_1:
					if e.Type == sdl.KEYDOWN {
						v.ResizeEvent(256, 240)
					}
				case sdl.K_2:
					if e.Type == sdl.KEYDOWN {
						v.ResizeEvent(512, 480)
					}
				case sdl.K_3:
					if e.Type == sdl.KEYDOWN {
						v.ResizeEvent(768, 720)
					}
				case sdl.K_4:
					if e.Type == sdl.KEYDOWN {
						v.ResizeEvent(1024, 960)
					}
				}

				switch e.Type {
				case sdl.KEYDOWN:
					nes.Pads[0].KeyDown(e, 0)
				case sdl.KEYUP:
					nes.Pads[0].KeyUp(e, 0)
				}
			}
		}
	}
}
示例#3
0
func (video *SDLVideo) Run() {
	running := true
	frame := make([]uint32, 0xf000)

	for running {
		select {
		case ev := <-sdl.Events:
			var event Event

			switch e := ev.(type) {
			case sdl.QuitEvent:
				running = false
				event = &QuitEvent{}
			case sdl.KeyboardEvent:
				switch e.Keysym.Sym {
				case sdl.K_BACKQUOTE:
					if e.Type == sdl.KEYDOWN {
						video.overscan = !video.overscan
					}
				case sdl.K_1:
					if e.Type == sdl.KEYDOWN {
						video.ResizeEvent(256, 240)
					}
				case sdl.K_2:
					if e.Type == sdl.KEYDOWN {
						video.ResizeEvent(512, 480)
					}
				case sdl.K_3:
					if e.Type == sdl.KEYDOWN {
						video.ResizeEvent(768, 720)
					}
				case sdl.K_4:
					if e.Type == sdl.KEYDOWN {
						video.ResizeEvent(1024, 960)
					}
				case sdl.K_5:
					if e.Type == sdl.KEYDOWN {
						video.ResizeEvent(2560, 1440)
					}
				case sdl.K_p:
					if e.Type == sdl.KEYDOWN {
						event = &PauseEvent{}
					}
				case sdl.K_n:
					if e.Type == sdl.KEYDOWN {
						event = &FrameStepEvent{}
					}
				case sdl.K_q:
					if e.Type == sdl.KEYDOWN {
						running = false
						event = &QuitEvent{}
					}
				case sdl.K_l:
					if e.Type == sdl.KEYDOWN {
						event = &SavePatternTablesEvent{}
					}
				case sdl.K_r:
					if e.Type == sdl.KEYDOWN {
						event = &ResetEvent{}
					}
				case sdl.K_s:
					if e.Type == sdl.KEYDOWN {
						event = &RecordEvent{}
					}
				case sdl.K_d:
					if e.Type == sdl.KEYDOWN {
						event = &StopEvent{}
					}
				case sdl.K_KP_PLUS:
					if e.Type == sdl.KEYDOWN {
						event = &AudioRecordEvent{}
					}
				case sdl.K_KP_MINUS:
					if e.Type == sdl.KEYDOWN {
						event = &AudioStopEvent{}
					}

				case sdl.K_o:
					if e.Type == sdl.KEYDOWN {
						event = &CPUDecodeEvent{}
					}
				case sdl.K_i:
					if e.Type == sdl.KEYDOWN {
						event = &PPUDecodeEvent{}
					}
				case sdl.K_9:
					if e.Type == sdl.KEYDOWN {
						event = &ShowBackgroundEvent{}
					}
				case sdl.K_0:
					if e.Type == sdl.KEYDOWN {
						event = &ShowSpritesEvent{}
					}
				case sdl.K_F1:
					if e.Type == sdl.KEYDOWN {
						event = &SaveStateEvent{}
					}
				case sdl.K_F5:
					if e.Type == sdl.KEYDOWN {
						event = &LoadStateEvent{}
					}
				case sdl.K_F8:
					if e.Type == sdl.KEYDOWN {
						event = &FPSEvent{2.}
					}
				case sdl.K_F9:
					if e.Type == sdl.KEYDOWN {
						event = &FPSEvent{1.}
					}
				case sdl.K_F10:
					if e.Type == sdl.KEYDOWN {
						event = &FPSEvent{.75}
					}
				case sdl.K_F11:
					if e.Type == sdl.KEYDOWN {
						event = &FPSEvent{.5}
					}
				case sdl.K_F12:
					if e.Type == sdl.KEYDOWN {
						event = &FPSEvent{.25}
					}
				case sdl.K_KP0:
					if e.Type == sdl.KEYDOWN {
						event = &MuteEvent{}
					}
				case sdl.K_KP1:
					if e.Type == sdl.KEYDOWN {
						event = &MutePulse1Event{}
					}
				case sdl.K_KP2:
					if e.Type == sdl.KEYDOWN {
						event = &MutePulse2Event{}
					}
				case sdl.K_KP3:
					if e.Type == sdl.KEYDOWN {
						event = &MuteTriangleEvent{}
					}
				case sdl.K_KP4:
					if e.Type == sdl.KEYDOWN {
						event = &MuteNoiseEvent{}
					}
				case sdl.K_KP5:
					if e.Type == sdl.KEYDOWN {
						event = &MuteDMCEvent{}
					}
				}

				if event == nil && running {
					event = &ControllerEvent{
						Button: button(e),
						Down:   e.Type == sdl.KEYDOWN,
					}
				}
			}

			if event != nil {
				go func() { video.events <- event }()
			}
		case colors := <-video.input:
			index := 0
			x, y := 0, 0

			for _, c := range colors {
				if pixelInFrame(x, y, video.overscan) {
					frame[index] = video.palette[c]
					index++
				}

				switch x {
				case 255:
					x = 0
					y++
				default:
					x++
				}
			}
			video.framePool.Put(colors)

			gl.Clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT)

			video.prog.Use()

			gl.ActiveTexture(gl.TEXTURE0)
			video.texture.Bind(gl.TEXTURE_2D)

			gl.TexImage2D(gl.TEXTURE_2D, 0, 3, video.frameWidth(), video.frameHeight(), 0, gl.RGBA,
				gl.UNSIGNED_INT_8_8_8_8, frame)

			gl.DrawArrays(gl.TRIANGLES, 0, 6)

			if video.screen != nil {
				sdl.GL_SwapBuffers()
			}
		}
	}
}