mirror of
https://github.com/mattrberry/crab.git
synced 2025-01-13 20:01:38 +01:00
temp push for changing computers
This commit is contained in:
parent
4cfd5b6fa7
commit
71dba46e8b
4 changed files with 92 additions and 6 deletions
|
@ -81,3 +81,9 @@ macro log(value, newline = true)
|
||||||
{% end %}
|
{% end %}
|
||||||
{% end %}
|
{% end %}
|
||||||
end
|
end
|
||||||
|
|
||||||
|
struct Slice(T)
|
||||||
|
def [](index : Int, t : R.class, index_r : Int) : R forall R
|
||||||
|
Pointer(R).new((self.to_unsafe + index).address)[index_r]
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
|
@ -325,15 +325,83 @@ module GBA
|
||||||
end
|
end
|
||||||
|
|
||||||
def calculate_color(col : Int) : UInt16
|
def calculate_color(col : Int) : UInt16
|
||||||
enables, effects = get_enables(col)
|
enable_flags, effects_enabled = get_enables(col)
|
||||||
top_color = nil
|
top_color = nil
|
||||||
|
colors = uninitialized Color[5]
|
||||||
|
sprite_pixel = @sprite_pixels[col]
|
||||||
|
colors[0] = Color.new(
|
||||||
|
sprite_pixel.priority,
|
||||||
|
sprite_pixel.palette,
|
||||||
|
sprite_pixel.blends,
|
||||||
|
4, # sprites are bit 4 in the enable flags
|
||||||
|
true, # sprite
|
||||||
|
)
|
||||||
|
4.times do |bg|
|
||||||
|
colors[bg + 1] = Color.new(
|
||||||
|
@bgcnt[bg].priority,
|
||||||
|
@layer_palettes[bg][col],
|
||||||
|
true, # backgrounds always blend
|
||||||
|
bg,
|
||||||
|
false, # not a sprite
|
||||||
|
)
|
||||||
|
end
|
||||||
4.times do |priority|
|
4.times do |priority|
|
||||||
if bit?(enables, 4)
|
colors.each do |color|
|
||||||
|
if bit?(enable_flags, color.target_bit) # check that layer is enabled
|
||||||
|
if color.priority == priority # check that priority matches (effectively orders backgrounds)
|
||||||
|
if top_color.nil?
|
||||||
|
if color.palette > 0 # check that color is opaque
|
||||||
|
if !effects_enabled || !color.blends # if effects are disabled, always take the first opaque color
|
||||||
|
return BGR16.new(@pram, color).value
|
||||||
|
elsif @bldcnt.is_bg_target(color.target_bit, target: 1)
|
||||||
|
top_color = color
|
||||||
|
end
|
||||||
|
end
|
||||||
|
else # top color has been selected
|
||||||
|
top_color_u16 = BGR16.new(@pram, top_color).value
|
||||||
|
if !@bldcnt.is_bg_target(color.target_bit, target: 2) # second layer isn't set in bldcnt, don't blend
|
||||||
|
return top_color_u16
|
||||||
|
elsif color.palette > 0 # is a target and color is opaque
|
||||||
|
if @bldcnt.blending_mode == 1 || top_color.sprite
|
||||||
|
return (BGR16.new(@pram, top_color) * (Math.min(16, @bldalpha.eva_coefficient) / 16) +
|
||||||
|
BGR16.new(@pram, color) * (Math.min(16, @bldalpha.evb_coefficient) / 16)).value
|
||||||
|
elsif @bldcnt.blending_mode == 0
|
||||||
|
return top_color_u16
|
||||||
|
elsif @bldcnt.blending_mode == 2
|
||||||
|
# blend with white
|
||||||
|
return top_color_u16 # todo
|
||||||
|
elsif @bldcnt.blending_mode == 3
|
||||||
|
# blend with black
|
||||||
|
return top_color_u16 # todo
|
||||||
|
end
|
||||||
|
else # is a target and color is transparent
|
||||||
|
if @bldcnt.blending_mode == 0
|
||||||
|
return top_color_u16
|
||||||
|
elsif @bldcnt.blending_mode == 1
|
||||||
|
return top_color_u16
|
||||||
|
elsif @bldcnt.blending_mode == 2
|
||||||
|
# blend with white
|
||||||
|
return top_color_u16 # todo
|
||||||
|
elsif @bldcnt.blending_mode == 3
|
||||||
|
# blend with black
|
||||||
|
return top_color_u16 # todo
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
backdrop_color = @pram.to_unsafe.as(UInt16*)[0]
|
||||||
|
return top_color.nil? ? backdrop_color : BGR16.new(@pram, top_color).value
|
||||||
|
|
||||||
|
4.times do |priority|
|
||||||
|
if bit?(enable_flags, 4)
|
||||||
sprite_pixel = @sprite_pixels[col]
|
sprite_pixel = @sprite_pixels[col]
|
||||||
if sprite_pixel.priority == priority && sprite_pixel.palette > 0
|
if sprite_pixel.priority == priority && sprite_pixel.palette > 0
|
||||||
selected_color = (@pram + 0x200).to_unsafe.as(UInt16*)[sprite_pixel.palette]
|
selected_color = (@pram + 0x200).to_unsafe.as(UInt16*)[sprite_pixel.palette]
|
||||||
if top_color.nil? # todo: brightness for sprites
|
if top_color.nil? # todo: brightness for sprites
|
||||||
if !(sprite_pixel.blends || (@bldcnt.is_bg_target(4, target: 1) && effects))
|
if !(sprite_pixel.blends || (@bldcnt.is_bg_target(4, target: 1) && effects_enabled))
|
||||||
return selected_color
|
return selected_color
|
||||||
elsif @bldcnt.color_special_effect == 1 # alpha blending
|
elsif @bldcnt.color_special_effect == 1 # alpha blending
|
||||||
top_color = selected_color
|
top_color = selected_color
|
||||||
|
@ -355,13 +423,13 @@ module GBA
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
4.times do |bg|
|
4.times do |bg|
|
||||||
if bit?(enables, bg)
|
if bit?(enable_flags, bg)
|
||||||
if @bgcnt[bg].priority == priority
|
if @bgcnt[bg].priority == priority
|
||||||
palette = @layer_palettes[bg][col]
|
palette = @layer_palettes[bg][col]
|
||||||
next if palette == 0
|
next if palette == 0
|
||||||
selected_color = @pram.to_unsafe.as(UInt16*)[palette]
|
selected_color = @pram.to_unsafe.as(UInt16*)[palette]
|
||||||
if top_color.nil?
|
if top_color.nil?
|
||||||
if @bldcnt.color_special_effect == 0 || !@bldcnt.is_bg_target(bg, target: 1) || !effects
|
if @bldcnt.color_special_effect == 0 || !@bldcnt.is_bg_target(bg, target: 1) || !effects_enabled
|
||||||
return selected_color
|
return selected_color
|
||||||
elsif @bldcnt.color_special_effect == 1 # alpha blending
|
elsif @bldcnt.color_special_effect == 1 # alpha blending
|
||||||
top_color = selected_color
|
top_color = selected_color
|
||||||
|
@ -427,6 +495,8 @@ module GBA
|
||||||
when 0x052..0x053 then @bldalpha.read_byte(io_addr & 1)
|
when 0x052..0x053 then @bldalpha.read_byte(io_addr & 1)
|
||||||
when 0x054..0x055 then @bldy.read_byte(io_addr & 1)
|
when 0x054..0x055 then @bldy.read_byte(io_addr & 1)
|
||||||
else log "Unmapped PPU read ~ addr:#{hex_str io_addr.to_u8}"; 0_u8 # todo: open bus
|
else log "Unmapped PPU read ~ addr:#{hex_str io_addr.to_u8}"; 0_u8 # todo: open bus
|
||||||
|
|
||||||
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -228,7 +228,7 @@ module GBA
|
||||||
bool bg2_2nd_target_pixel
|
bool bg2_2nd_target_pixel
|
||||||
bool bg1_2nd_target_pixel
|
bool bg1_2nd_target_pixel
|
||||||
bool bg0_2nd_target_pixel
|
bool bg0_2nd_target_pixel
|
||||||
num color_special_effect, 2
|
num blending_mode, 2
|
||||||
bool bd_1st_target_pixel
|
bool bd_1st_target_pixel
|
||||||
bool obj_1st_target_pixel
|
bool obj_1st_target_pixel
|
||||||
bool bg3_1st_target_pixel
|
bool bg3_1st_target_pixel
|
||||||
|
|
|
@ -3,6 +3,10 @@ module GBA
|
||||||
alias HalfWord = UInt16
|
alias HalfWord = UInt16
|
||||||
alias Word = UInt32
|
alias Word = UInt32
|
||||||
alias Words = Slice(UInt32)
|
alias Words = Slice(UInt32)
|
||||||
|
|
||||||
|
record Color, priority : Int32, palette : Int32, blends : Bool, target_bit : Int32, sprite : Bool do
|
||||||
|
end
|
||||||
|
|
||||||
record BGR16, value : UInt16 do # xBBBBBGGGGGRRRRR
|
record BGR16, value : UInt16 do # xBBBBBGGGGGRRRRR
|
||||||
# Create a new BGR16 struct with the given values. Trucates at 5 bits.
|
# Create a new BGR16 struct with the given values. Trucates at 5 bits.
|
||||||
def initialize(blue : Number, green : Number, red : Number)
|
def initialize(blue : Number, green : Number, red : Number)
|
||||||
|
@ -11,6 +15,12 @@ module GBA
|
||||||
(red <= 0x1F ? red.to_u16 : 0x1F_u16)
|
(red <= 0x1F ? red.to_u16 : 0x1F_u16)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def initialize(pram : Slice(UInt8), color : Color)
|
||||||
|
palette_base = pram.to_unsafe
|
||||||
|
palette_base += 0x200 if color.sprite
|
||||||
|
@value = palette_base.as(UInt16*)[color.palette]
|
||||||
|
end
|
||||||
|
|
||||||
def blue : UInt16
|
def blue : UInt16
|
||||||
bits(value, 0xA..0xE)
|
bits(value, 0xA..0xE)
|
||||||
end
|
end
|
||||||
|
|
Loading…
Reference in a new issue