我想在 MARS 位图显示中创建一个红色屏幕,而不是让边框变成黄色。
我首先将第一行和最后一行设为黄色,然后将第一列和最后一列设为黄色。
这是我的代码:
#MIPS
#ND
#1 b
li $t0, -4 #$t0 holds current iterator
li $s0, 0 #Current COLOMN_iterator
li $s1, 0 #Current ROW_iterator
main:
li $t1, 0x00ff0000 #Loading RED in register
li $t2, 0x00ffff00 #Loading YELLOW in register
addi $gp, $gp, 4 #Incrementing register with one word (next pixel in display)
addi $t0, $t0, 4 #Incrementing current location to next pixel
addi $s0, $s0, 1 #Column++
blt $s1, 1, makePixelYellow #if currentRow == 1
beq $s1, 31, makePixelYellow #if currentRow == 31
j makePixelRed
makePixelYellow:
sw $t2, -4($gp) #Make pixel yellow
bne $s0, 32, main
addi $s1, $s1, 1 #Column finsihed, so row++
li $s0, 0 #Resetting column
j main
makePixelRed:
sw $t1, -4($gp) #Make pixel red
j main
我认为问题出现在第 19 行的某个地方。我可以使用 Branch-less not 将特定 n 下面的所有行设为黄色。但我无法使用 Branch-equal 为某一特定行着色。
标签仅在分支小于上正确执行,而不是在分支等于上正确执行。 顺便说一句,这是 MIPS ASM。
最佳答案
Jester 的回答:当您分支到 makePixelRed
代码时,您不会更新行/列。
我对计算机图形编程的一般建议:
通常在编写一些像素图形时,您不想按像素进行分支,这在性能方面非常昂贵,而针对性能的代码则相反,而是发出更多涵盖不同情况的代码路径来绘制所需的输出涉及最少的分支。
“计算某些内容+大量分支+绘制单个像素+循环”仅在性能不重要时使用,但您只想使用单个通用代码来进行像素绘制和循环(例如列/行前进,其中如果您仅使用这些分支来设置黄色/红色像素,然后返回到某个“主”结尾以完成循环代码,那么实际上可以使您避免错误,就像在某些光线跟踪器代码中,或者在最小二进制上进行编码时大小(256B 介绍经常使用这种架构,一个相当复杂的公式来计算像素颜色,然后单个 setPixel 代码和循环 = 它很慢,但由于没有到处都有多个 setPixel 副本,因此节省了许多字节)。
这是我的一些更直接的“设置黄色边框+红色主体”示例(使用 MARS 4.5 进行测试,延迟分支关闭,并且我使用了与您相同的位图设置(16x16 单元,512x256 显示,这意味着 32x16 位图目标..用户体验FTW!)
li $t1, 0x00ff0000 #Loading RED in register
li $t2, 0x00ffff00 #Loading YELLOW in register
big_loop:
# top row + first column
move $a0, $gp # pointer to write to
li $a1, 33 # 32 pixels for first row, +1 for left column
move $a2, $t2 # yellow
jal setPixels
# 14 red rows with yellow endings+starts
li $t0, 14
red_rows_loop:
li $a1, 30
move $a2, $t1
jal setPixels # set 30 red pixels in middle
sw $t2, ($a0) # set 1 yellow at end, and 1 at start of next row
sw $t2, 4($a0)
addi $a0, $a0, 8
addi $t0, $t0, -1
bnez $t0, red_rows_loop
# finish last row to be full yellow
li $a1, 31 # 31 pixels more needed (1 is already there)
move $a2, $t2 # yellow
jal setPixels
li $v0, 32 # MARS service delay(ms)
li $a0, 40 # 40ms = ~25 FPS if the draw would be instant
syscall
addiu $t1, $t1, 0xFE0408 # adjust main color (red -2, green +4, blue +8 + overflows (B -> G -> R)
andi $t1, $t1, 0xFFFFFF # force "alpha" to zero
j big_loop # infinite loop will animated colours...
# Sets $a1 pixels to $a2 value starting at $a0 (memory fill)
# a0 = pointer to write to, a1 = count of pixels, a2 = value of pixel to set
# a0 will be updated to point right after the last written word
setPixels:
sw $a2, ($a0) # set pixel (or simply memory word)
addi $a0, $a0, 4 # advance memory pointer
addi $a1, $a1, -1 # count-down loop
bnez $a1, setPixels
jr $ra # return
关于assembly - 位图 ASM 中的颜色特定行,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47602199/