Ctrl-F6: Show a split screen with the views for NTSC color TV, monochrome monitor, HGR page 1 and HGR page 2
This commit is contained in:
parent
b375869923
commit
dad2a67321
|
@ -120,6 +120,7 @@ Line:
|
||||||
- F5: Toggle speed between real and fastest
|
- F5: Toggle speed between real and fastest
|
||||||
- Ctrl-F5: Show current speed in Mhz
|
- Ctrl-F5: Show current speed in Mhz
|
||||||
- F6: Toggle between NTSC color TV and green phosphor monochrome monitor
|
- F6: Toggle between NTSC color TV and green phosphor monochrome monitor
|
||||||
|
- Ctrl-F6: Show a split screen with the views for NTSC color TV, monochrome monitor, HGR page 1 and HGR page 2.
|
||||||
- F7: Save current state to disk (incomplete)
|
- F7: Save current state to disk (incomplete)
|
||||||
- F8: Restore state from disk (incomplete)
|
- F8: Restore state from disk (incomplete)
|
||||||
- F10: Cycle character generator codepages. Only if the character generator ROM has more than one 2Kb page.
|
- F10: Cycle character generator codepages. Only if the character generator ROM has more than one 2Kb page.
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
package main
|
package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"image"
|
||||||
"unsafe"
|
"unsafe"
|
||||||
|
|
||||||
"github.com/ivanizag/apple2"
|
"github.com/ivanizag/apple2"
|
||||||
|
@ -77,7 +78,12 @@ func SDLRun(a *apple2.Apple2) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if !a.IsPaused() {
|
if !a.IsPaused() {
|
||||||
img := apple2.Snapshot(a)
|
var img *image.RGBA
|
||||||
|
if kp.showPages {
|
||||||
|
img = apple2.SnapshotHGRModes(a)
|
||||||
|
} else {
|
||||||
|
img = apple2.Snapshot(a)
|
||||||
|
}
|
||||||
if img != nil {
|
if img != nil {
|
||||||
surface, err := sdl.CreateRGBSurfaceFrom(unsafe.Pointer(&img.Pix[0]),
|
surface, err := sdl.CreateRGBSurfaceFrom(unsafe.Pointer(&img.Pix[0]),
|
||||||
int32(img.Bounds().Dx()), int32(img.Bounds().Dy()),
|
int32(img.Bounds().Dx()), int32(img.Bounds().Dy()),
|
||||||
|
|
|
@ -11,6 +11,8 @@ import (
|
||||||
type sdlKeyboard struct {
|
type sdlKeyboard struct {
|
||||||
keyChannel chan uint8
|
keyChannel chan uint8
|
||||||
a *apple2.Apple2
|
a *apple2.Apple2
|
||||||
|
|
||||||
|
showPages bool
|
||||||
}
|
}
|
||||||
|
|
||||||
func newSDLKeyBoard(a *apple2.Apple2) *sdlKeyboard {
|
func newSDLKeyBoard(a *apple2.Apple2) *sdlKeyboard {
|
||||||
|
@ -105,7 +107,11 @@ func (k *sdlKeyboard) putKey(keyEvent *sdl.KeyboardEvent) {
|
||||||
k.a.SendCommand(apple2.CommandToggleSpeed)
|
k.a.SendCommand(apple2.CommandToggleSpeed)
|
||||||
}
|
}
|
||||||
case sdl.K_F6:
|
case sdl.K_F6:
|
||||||
k.a.SendCommand(apple2.CommandToggleColor)
|
if ctrl {
|
||||||
|
k.showPages = !k.showPages
|
||||||
|
} else {
|
||||||
|
k.a.SendCommand(apple2.CommandToggleColor)
|
||||||
|
}
|
||||||
case sdl.K_F7:
|
case sdl.K_F7:
|
||||||
k.a.SendCommand(apple2.CommandSaveState)
|
k.a.SendCommand(apple2.CommandSaveState)
|
||||||
case sdl.K_F8:
|
case sdl.K_F8:
|
||||||
|
|
49
screen.go
49
screen.go
|
@ -17,6 +17,10 @@ References:
|
||||||
|
|
||||||
// Snapshot the currently visible screen
|
// Snapshot the currently visible screen
|
||||||
func Snapshot(a *Apple2) *image.RGBA {
|
func Snapshot(a *Apple2) *image.RGBA {
|
||||||
|
return activeSnapshot(a, false)
|
||||||
|
}
|
||||||
|
|
||||||
|
func activeSnapshot(a *Apple2, raw bool) *image.RGBA {
|
||||||
isColor := a.isColor
|
isColor := a.isColor
|
||||||
isTextMode := a.io.isSoftSwitchActive(ioFlagText)
|
isTextMode := a.io.isSoftSwitchActive(ioFlagText)
|
||||||
isHiResMode := a.io.isSoftSwitchActive(ioFlagHiRes)
|
isHiResMode := a.io.isSoftSwitchActive(ioFlagHiRes)
|
||||||
|
@ -56,17 +60,42 @@ func Snapshot(a *Apple2) *image.RGBA {
|
||||||
snapText := snapshotTextMode(a, is80Columns, false /*isSecondPage*/, true /*isMixMode*/, lightColor)
|
snapText := snapshotTextMode(a, is80Columns, false /*isSecondPage*/, true /*isMixMode*/, lightColor)
|
||||||
snap = mixSnapshots(snap, snapText)
|
snap = mixSnapshots(snap, snapText)
|
||||||
}
|
}
|
||||||
if isColor {
|
if isColor && !raw {
|
||||||
snap = filterNTSCColor(false /*blacker*/, snap)
|
snap = filterNTSCColor(false /*blacker*/, snap)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if !isSuperHighResMode {
|
if !raw && !isSuperHighResMode {
|
||||||
snap = linesSeparatedFilter(snap)
|
snap = linesSeparatedFilter(snap)
|
||||||
}
|
}
|
||||||
return snap
|
return snap
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SnapshotAllModes to get all modes mixed
|
||||||
|
func SnapshotHGRModes(a *Apple2) *image.RGBA {
|
||||||
|
bwSnap := activeSnapshot(a, true)
|
||||||
|
if bwSnap.Bounds().Dx() == hiResWidth {
|
||||||
|
bwSnap = doubleWidthFilter(bwSnap)
|
||||||
|
}
|
||||||
|
colorSnap := filterNTSCColor(false, bwSnap)
|
||||||
|
page1Snap := filterNTSCColor(false /*blacker*/, snapshotHiResModeMono(a, false /*2nd page*/, false /*mix*/, color.White)) // HGR 1
|
||||||
|
page2Snap := filterNTSCColor(false /*blacker*/, snapshotHiResModeMono(a, true /*2nd page*/, false /*mix*/, color.White)) // HGR 2
|
||||||
|
|
||||||
|
size := image.Rect(0, 0, hiResWidth*4, hiResHeight*2)
|
||||||
|
out := image.NewRGBA(size)
|
||||||
|
|
||||||
|
for y := 0; y < hiResHeight; y++ {
|
||||||
|
for x := 0; x < hiResWidth*2; x++ {
|
||||||
|
out.Set(x, y, colorSnap.At(x, y))
|
||||||
|
out.Set(x+hiResWidth*2, y, bwSnap.At(x, y))
|
||||||
|
out.Set(x, y+hiResHeight, page1Snap.At(x, y))
|
||||||
|
out.Set(x+hiResWidth*2, y+hiResHeight, page2Snap.At(x, y))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
|
||||||
func mixSnapshots(top, bottom *image.RGBA) *image.RGBA {
|
func mixSnapshots(top, bottom *image.RGBA) *image.RGBA {
|
||||||
topBounds := top.Bounds()
|
topBounds := top.Bounds()
|
||||||
topWidth := topBounds.Dx()
|
topWidth := topBounds.Dx()
|
||||||
|
@ -89,7 +118,7 @@ func mixSnapshots(top, bottom *image.RGBA) *image.RGBA {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Copy bottom, applyng the factor
|
// Copy bottom, applying the factor
|
||||||
for y := bottomBounds.Min.Y; y < bottomBounds.Max.Y; y++ {
|
for y := bottomBounds.Min.Y; y < bottomBounds.Max.Y; y++ {
|
||||||
for x := bottomBounds.Min.X; x < bottomBounds.Max.X; x++ {
|
for x := bottomBounds.Min.X; x < bottomBounds.Max.X; x++ {
|
||||||
c := bottom.At(x, y)
|
c := bottom.At(x, y)
|
||||||
|
@ -149,3 +178,17 @@ func linesSeparatedFilter(in *image.RGBA) *image.RGBA {
|
||||||
}
|
}
|
||||||
return out
|
return out
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func doubleWidthFilter(in *image.RGBA) *image.RGBA {
|
||||||
|
b := in.Bounds()
|
||||||
|
size := image.Rect(0, 0, 2*b.Dx(), b.Dy())
|
||||||
|
out := image.NewRGBA(size)
|
||||||
|
for y := b.Min.Y; y < b.Max.Y; y++ {
|
||||||
|
for x := b.Min.X; x < b.Max.X; x++ {
|
||||||
|
c := in.At(x, y)
|
||||||
|
out.Set(2*x, y, c)
|
||||||
|
out.Set(2*x+1, y, c)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in New Issue