...

Source file src/golang.org/x/image/vp8/predfunc.go

Documentation: golang.org/x/image/vp8

     1  // Copyright 2011 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package vp8
     6  
     7  // This file implements the predicition functions, as specified in chapter 12.
     8  //
     9  // For each macroblock (of 1x16x16 luma and 2x8x8 chroma coefficients), the
    10  // luma values are either predicted as one large 16x16 region or 16 separate
    11  // 4x4 regions. The chroma values are always predicted as one 8x8 region.
    12  //
    13  // For 4x4 regions, the target block's predicted values (Xs) are a function of
    14  // its previously-decoded top and left border values, as well as a number of
    15  // pixels from the top-right:
    16  //
    17  //	a b c d e f g h
    18  //	p X X X X
    19  //	q X X X X
    20  //	r X X X X
    21  //	s X X X X
    22  //
    23  // The predictor modes are:
    24  //	- DC: all Xs = (b + c + d + e + p + q + r + s + 4) / 8.
    25  //	- TM: the first X = (b + p - a), the second X = (c + p - a), and so on.
    26  //	- VE: each X = the weighted average of its column's top value and that
    27  //	      value's neighbors, i.e. averages of abc, bcd, cde or def.
    28  //	- HE: similar to VE except rows instead of columns, and the final row is
    29  //	      an average of r, s and s.
    30  //	- RD, VR, LD, VL, HD, HU: these diagonal modes ("Right Down", "Vertical
    31  //	      Right", etc) are more complicated and are described in section 12.3.
    32  // All Xs are clipped to the range [0, 255].
    33  //
    34  // For 8x8 and 16x16 regions, the target block's predicted values are a
    35  // function of the top and left border values without the top-right overhang,
    36  // i.e. without the 8x8 or 16x16 equivalent of f, g and h. Furthermore:
    37  //	- There are no diagonal predictor modes, only DC, TM, VE and HE.
    38  //	- The DC mode has variants for macroblocks in the top row and/or left
    39  //	  column, i.e. for macroblocks with mby == 0 || mbx == 0.
    40  //	- The VE and HE modes take only the column top or row left values; they do
    41  //	  not smooth that top/left value with its neighbors.
    42  
    43  // nPred is the number of predictor modes, not including the Top/Left versions
    44  // of the DC predictor mode.
    45  const nPred = 10
    46  
    47  const (
    48  	predDC = iota
    49  	predTM
    50  	predVE
    51  	predHE
    52  	predRD
    53  	predVR
    54  	predLD
    55  	predVL
    56  	predHD
    57  	predHU
    58  	predDCTop
    59  	predDCLeft
    60  	predDCTopLeft
    61  )
    62  
    63  func checkTopLeftPred(mbx, mby int, p uint8) uint8 {
    64  	if p != predDC {
    65  		return p
    66  	}
    67  	if mbx == 0 {
    68  		if mby == 0 {
    69  			return predDCTopLeft
    70  		}
    71  		return predDCLeft
    72  	}
    73  	if mby == 0 {
    74  		return predDCTop
    75  	}
    76  	return predDC
    77  }
    78  
    79  var predFunc4 = [...]func(*Decoder, int, int){
    80  	predFunc4DC,
    81  	predFunc4TM,
    82  	predFunc4VE,
    83  	predFunc4HE,
    84  	predFunc4RD,
    85  	predFunc4VR,
    86  	predFunc4LD,
    87  	predFunc4VL,
    88  	predFunc4HD,
    89  	predFunc4HU,
    90  	nil,
    91  	nil,
    92  	nil,
    93  }
    94  
    95  var predFunc8 = [...]func(*Decoder, int, int){
    96  	predFunc8DC,
    97  	predFunc8TM,
    98  	predFunc8VE,
    99  	predFunc8HE,
   100  	nil,
   101  	nil,
   102  	nil,
   103  	nil,
   104  	nil,
   105  	nil,
   106  	predFunc8DCTop,
   107  	predFunc8DCLeft,
   108  	predFunc8DCTopLeft,
   109  }
   110  
   111  var predFunc16 = [...]func(*Decoder, int, int){
   112  	predFunc16DC,
   113  	predFunc16TM,
   114  	predFunc16VE,
   115  	predFunc16HE,
   116  	nil,
   117  	nil,
   118  	nil,
   119  	nil,
   120  	nil,
   121  	nil,
   122  	predFunc16DCTop,
   123  	predFunc16DCLeft,
   124  	predFunc16DCTopLeft,
   125  }
   126  
   127  func predFunc4DC(z *Decoder, y, x int) {
   128  	sum := uint32(4)
   129  	for i := 0; i < 4; i++ {
   130  		sum += uint32(z.ybr[y-1][x+i])
   131  	}
   132  	for j := 0; j < 4; j++ {
   133  		sum += uint32(z.ybr[y+j][x-1])
   134  	}
   135  	avg := uint8(sum / 8)
   136  	for j := 0; j < 4; j++ {
   137  		for i := 0; i < 4; i++ {
   138  			z.ybr[y+j][x+i] = avg
   139  		}
   140  	}
   141  }
   142  
   143  func predFunc4TM(z *Decoder, y, x int) {
   144  	delta0 := -int32(z.ybr[y-1][x-1])
   145  	for j := 0; j < 4; j++ {
   146  		delta1 := delta0 + int32(z.ybr[y+j][x-1])
   147  		for i := 0; i < 4; i++ {
   148  			delta2 := delta1 + int32(z.ybr[y-1][x+i])
   149  			z.ybr[y+j][x+i] = uint8(clip(delta2, 0, 255))
   150  		}
   151  	}
   152  }
   153  
   154  func predFunc4VE(z *Decoder, y, x int) {
   155  	a := int32(z.ybr[y-1][x-1])
   156  	b := int32(z.ybr[y-1][x+0])
   157  	c := int32(z.ybr[y-1][x+1])
   158  	d := int32(z.ybr[y-1][x+2])
   159  	e := int32(z.ybr[y-1][x+3])
   160  	f := int32(z.ybr[y-1][x+4])
   161  	abc := uint8((a + 2*b + c + 2) / 4)
   162  	bcd := uint8((b + 2*c + d + 2) / 4)
   163  	cde := uint8((c + 2*d + e + 2) / 4)
   164  	def := uint8((d + 2*e + f + 2) / 4)
   165  	for j := 0; j < 4; j++ {
   166  		z.ybr[y+j][x+0] = abc
   167  		z.ybr[y+j][x+1] = bcd
   168  		z.ybr[y+j][x+2] = cde
   169  		z.ybr[y+j][x+3] = def
   170  	}
   171  }
   172  
   173  func predFunc4HE(z *Decoder, y, x int) {
   174  	s := int32(z.ybr[y+3][x-1])
   175  	r := int32(z.ybr[y+2][x-1])
   176  	q := int32(z.ybr[y+1][x-1])
   177  	p := int32(z.ybr[y+0][x-1])
   178  	a := int32(z.ybr[y-1][x-1])
   179  	ssr := uint8((s + 2*s + r + 2) / 4)
   180  	srq := uint8((s + 2*r + q + 2) / 4)
   181  	rqp := uint8((r + 2*q + p + 2) / 4)
   182  	apq := uint8((a + 2*p + q + 2) / 4)
   183  	for i := 0; i < 4; i++ {
   184  		z.ybr[y+0][x+i] = apq
   185  		z.ybr[y+1][x+i] = rqp
   186  		z.ybr[y+2][x+i] = srq
   187  		z.ybr[y+3][x+i] = ssr
   188  	}
   189  }
   190  
   191  func predFunc4RD(z *Decoder, y, x int) {
   192  	s := int32(z.ybr[y+3][x-1])
   193  	r := int32(z.ybr[y+2][x-1])
   194  	q := int32(z.ybr[y+1][x-1])
   195  	p := int32(z.ybr[y+0][x-1])
   196  	a := int32(z.ybr[y-1][x-1])
   197  	b := int32(z.ybr[y-1][x+0])
   198  	c := int32(z.ybr[y-1][x+1])
   199  	d := int32(z.ybr[y-1][x+2])
   200  	e := int32(z.ybr[y-1][x+3])
   201  	srq := uint8((s + 2*r + q + 2) / 4)
   202  	rqp := uint8((r + 2*q + p + 2) / 4)
   203  	qpa := uint8((q + 2*p + a + 2) / 4)
   204  	pab := uint8((p + 2*a + b + 2) / 4)
   205  	abc := uint8((a + 2*b + c + 2) / 4)
   206  	bcd := uint8((b + 2*c + d + 2) / 4)
   207  	cde := uint8((c + 2*d + e + 2) / 4)
   208  	z.ybr[y+0][x+0] = pab
   209  	z.ybr[y+0][x+1] = abc
   210  	z.ybr[y+0][x+2] = bcd
   211  	z.ybr[y+0][x+3] = cde
   212  	z.ybr[y+1][x+0] = qpa
   213  	z.ybr[y+1][x+1] = pab
   214  	z.ybr[y+1][x+2] = abc
   215  	z.ybr[y+1][x+3] = bcd
   216  	z.ybr[y+2][x+0] = rqp
   217  	z.ybr[y+2][x+1] = qpa
   218  	z.ybr[y+2][x+2] = pab
   219  	z.ybr[y+2][x+3] = abc
   220  	z.ybr[y+3][x+0] = srq
   221  	z.ybr[y+3][x+1] = rqp
   222  	z.ybr[y+3][x+2] = qpa
   223  	z.ybr[y+3][x+3] = pab
   224  }
   225  
   226  func predFunc4VR(z *Decoder, y, x int) {
   227  	r := int32(z.ybr[y+2][x-1])
   228  	q := int32(z.ybr[y+1][x-1])
   229  	p := int32(z.ybr[y+0][x-1])
   230  	a := int32(z.ybr[y-1][x-1])
   231  	b := int32(z.ybr[y-1][x+0])
   232  	c := int32(z.ybr[y-1][x+1])
   233  	d := int32(z.ybr[y-1][x+2])
   234  	e := int32(z.ybr[y-1][x+3])
   235  	ab := uint8((a + b + 1) / 2)
   236  	bc := uint8((b + c + 1) / 2)
   237  	cd := uint8((c + d + 1) / 2)
   238  	de := uint8((d + e + 1) / 2)
   239  	rqp := uint8((r + 2*q + p + 2) / 4)
   240  	qpa := uint8((q + 2*p + a + 2) / 4)
   241  	pab := uint8((p + 2*a + b + 2) / 4)
   242  	abc := uint8((a + 2*b + c + 2) / 4)
   243  	bcd := uint8((b + 2*c + d + 2) / 4)
   244  	cde := uint8((c + 2*d + e + 2) / 4)
   245  	z.ybr[y+0][x+0] = ab
   246  	z.ybr[y+0][x+1] = bc
   247  	z.ybr[y+0][x+2] = cd
   248  	z.ybr[y+0][x+3] = de
   249  	z.ybr[y+1][x+0] = pab
   250  	z.ybr[y+1][x+1] = abc
   251  	z.ybr[y+1][x+2] = bcd
   252  	z.ybr[y+1][x+3] = cde
   253  	z.ybr[y+2][x+0] = qpa
   254  	z.ybr[y+2][x+1] = ab
   255  	z.ybr[y+2][x+2] = bc
   256  	z.ybr[y+2][x+3] = cd
   257  	z.ybr[y+3][x+0] = rqp
   258  	z.ybr[y+3][x+1] = pab
   259  	z.ybr[y+3][x+2] = abc
   260  	z.ybr[y+3][x+3] = bcd
   261  }
   262  
   263  func predFunc4LD(z *Decoder, y, x int) {
   264  	a := int32(z.ybr[y-1][x+0])
   265  	b := int32(z.ybr[y-1][x+1])
   266  	c := int32(z.ybr[y-1][x+2])
   267  	d := int32(z.ybr[y-1][x+3])
   268  	e := int32(z.ybr[y-1][x+4])
   269  	f := int32(z.ybr[y-1][x+5])
   270  	g := int32(z.ybr[y-1][x+6])
   271  	h := int32(z.ybr[y-1][x+7])
   272  	abc := uint8((a + 2*b + c + 2) / 4)
   273  	bcd := uint8((b + 2*c + d + 2) / 4)
   274  	cde := uint8((c + 2*d + e + 2) / 4)
   275  	def := uint8((d + 2*e + f + 2) / 4)
   276  	efg := uint8((e + 2*f + g + 2) / 4)
   277  	fgh := uint8((f + 2*g + h + 2) / 4)
   278  	ghh := uint8((g + 2*h + h + 2) / 4)
   279  	z.ybr[y+0][x+0] = abc
   280  	z.ybr[y+0][x+1] = bcd
   281  	z.ybr[y+0][x+2] = cde
   282  	z.ybr[y+0][x+3] = def
   283  	z.ybr[y+1][x+0] = bcd
   284  	z.ybr[y+1][x+1] = cde
   285  	z.ybr[y+1][x+2] = def
   286  	z.ybr[y+1][x+3] = efg
   287  	z.ybr[y+2][x+0] = cde
   288  	z.ybr[y+2][x+1] = def
   289  	z.ybr[y+2][x+2] = efg
   290  	z.ybr[y+2][x+3] = fgh
   291  	z.ybr[y+3][x+0] = def
   292  	z.ybr[y+3][x+1] = efg
   293  	z.ybr[y+3][x+2] = fgh
   294  	z.ybr[y+3][x+3] = ghh
   295  }
   296  
   297  func predFunc4VL(z *Decoder, y, x int) {
   298  	a := int32(z.ybr[y-1][x+0])
   299  	b := int32(z.ybr[y-1][x+1])
   300  	c := int32(z.ybr[y-1][x+2])
   301  	d := int32(z.ybr[y-1][x+3])
   302  	e := int32(z.ybr[y-1][x+4])
   303  	f := int32(z.ybr[y-1][x+5])
   304  	g := int32(z.ybr[y-1][x+6])
   305  	h := int32(z.ybr[y-1][x+7])
   306  	ab := uint8((a + b + 1) / 2)
   307  	bc := uint8((b + c + 1) / 2)
   308  	cd := uint8((c + d + 1) / 2)
   309  	de := uint8((d + e + 1) / 2)
   310  	abc := uint8((a + 2*b + c + 2) / 4)
   311  	bcd := uint8((b + 2*c + d + 2) / 4)
   312  	cde := uint8((c + 2*d + e + 2) / 4)
   313  	def := uint8((d + 2*e + f + 2) / 4)
   314  	efg := uint8((e + 2*f + g + 2) / 4)
   315  	fgh := uint8((f + 2*g + h + 2) / 4)
   316  	z.ybr[y+0][x+0] = ab
   317  	z.ybr[y+0][x+1] = bc
   318  	z.ybr[y+0][x+2] = cd
   319  	z.ybr[y+0][x+3] = de
   320  	z.ybr[y+1][x+0] = abc
   321  	z.ybr[y+1][x+1] = bcd
   322  	z.ybr[y+1][x+2] = cde
   323  	z.ybr[y+1][x+3] = def
   324  	z.ybr[y+2][x+0] = bc
   325  	z.ybr[y+2][x+1] = cd
   326  	z.ybr[y+2][x+2] = de
   327  	z.ybr[y+2][x+3] = efg
   328  	z.ybr[y+3][x+0] = bcd
   329  	z.ybr[y+3][x+1] = cde
   330  	z.ybr[y+3][x+2] = def
   331  	z.ybr[y+3][x+3] = fgh
   332  }
   333  
   334  func predFunc4HD(z *Decoder, y, x int) {
   335  	s := int32(z.ybr[y+3][x-1])
   336  	r := int32(z.ybr[y+2][x-1])
   337  	q := int32(z.ybr[y+1][x-1])
   338  	p := int32(z.ybr[y+0][x-1])
   339  	a := int32(z.ybr[y-1][x-1])
   340  	b := int32(z.ybr[y-1][x+0])
   341  	c := int32(z.ybr[y-1][x+1])
   342  	d := int32(z.ybr[y-1][x+2])
   343  	sr := uint8((s + r + 1) / 2)
   344  	rq := uint8((r + q + 1) / 2)
   345  	qp := uint8((q + p + 1) / 2)
   346  	pa := uint8((p + a + 1) / 2)
   347  	srq := uint8((s + 2*r + q + 2) / 4)
   348  	rqp := uint8((r + 2*q + p + 2) / 4)
   349  	qpa := uint8((q + 2*p + a + 2) / 4)
   350  	pab := uint8((p + 2*a + b + 2) / 4)
   351  	abc := uint8((a + 2*b + c + 2) / 4)
   352  	bcd := uint8((b + 2*c + d + 2) / 4)
   353  	z.ybr[y+0][x+0] = pa
   354  	z.ybr[y+0][x+1] = pab
   355  	z.ybr[y+0][x+2] = abc
   356  	z.ybr[y+0][x+3] = bcd
   357  	z.ybr[y+1][x+0] = qp
   358  	z.ybr[y+1][x+1] = qpa
   359  	z.ybr[y+1][x+2] = pa
   360  	z.ybr[y+1][x+3] = pab
   361  	z.ybr[y+2][x+0] = rq
   362  	z.ybr[y+2][x+1] = rqp
   363  	z.ybr[y+2][x+2] = qp
   364  	z.ybr[y+2][x+3] = qpa
   365  	z.ybr[y+3][x+0] = sr
   366  	z.ybr[y+3][x+1] = srq
   367  	z.ybr[y+3][x+2] = rq
   368  	z.ybr[y+3][x+3] = rqp
   369  }
   370  
   371  func predFunc4HU(z *Decoder, y, x int) {
   372  	s := int32(z.ybr[y+3][x-1])
   373  	r := int32(z.ybr[y+2][x-1])
   374  	q := int32(z.ybr[y+1][x-1])
   375  	p := int32(z.ybr[y+0][x-1])
   376  	pq := uint8((p + q + 1) / 2)
   377  	qr := uint8((q + r + 1) / 2)
   378  	rs := uint8((r + s + 1) / 2)
   379  	pqr := uint8((p + 2*q + r + 2) / 4)
   380  	qrs := uint8((q + 2*r + s + 2) / 4)
   381  	rss := uint8((r + 2*s + s + 2) / 4)
   382  	sss := uint8(s)
   383  	z.ybr[y+0][x+0] = pq
   384  	z.ybr[y+0][x+1] = pqr
   385  	z.ybr[y+0][x+2] = qr
   386  	z.ybr[y+0][x+3] = qrs
   387  	z.ybr[y+1][x+0] = qr
   388  	z.ybr[y+1][x+1] = qrs
   389  	z.ybr[y+1][x+2] = rs
   390  	z.ybr[y+1][x+3] = rss
   391  	z.ybr[y+2][x+0] = rs
   392  	z.ybr[y+2][x+1] = rss
   393  	z.ybr[y+2][x+2] = sss
   394  	z.ybr[y+2][x+3] = sss
   395  	z.ybr[y+3][x+0] = sss
   396  	z.ybr[y+3][x+1] = sss
   397  	z.ybr[y+3][x+2] = sss
   398  	z.ybr[y+3][x+3] = sss
   399  }
   400  
   401  func predFunc8DC(z *Decoder, y, x int) {
   402  	sum := uint32(8)
   403  	for i := 0; i < 8; i++ {
   404  		sum += uint32(z.ybr[y-1][x+i])
   405  	}
   406  	for j := 0; j < 8; j++ {
   407  		sum += uint32(z.ybr[y+j][x-1])
   408  	}
   409  	avg := uint8(sum / 16)
   410  	for j := 0; j < 8; j++ {
   411  		for i := 0; i < 8; i++ {
   412  			z.ybr[y+j][x+i] = avg
   413  		}
   414  	}
   415  }
   416  
   417  func predFunc8TM(z *Decoder, y, x int) {
   418  	delta0 := -int32(z.ybr[y-1][x-1])
   419  	for j := 0; j < 8; j++ {
   420  		delta1 := delta0 + int32(z.ybr[y+j][x-1])
   421  		for i := 0; i < 8; i++ {
   422  			delta2 := delta1 + int32(z.ybr[y-1][x+i])
   423  			z.ybr[y+j][x+i] = uint8(clip(delta2, 0, 255))
   424  		}
   425  	}
   426  }
   427  
   428  func predFunc8VE(z *Decoder, y, x int) {
   429  	for j := 0; j < 8; j++ {
   430  		for i := 0; i < 8; i++ {
   431  			z.ybr[y+j][x+i] = z.ybr[y-1][x+i]
   432  		}
   433  	}
   434  }
   435  
   436  func predFunc8HE(z *Decoder, y, x int) {
   437  	for j := 0; j < 8; j++ {
   438  		for i := 0; i < 8; i++ {
   439  			z.ybr[y+j][x+i] = z.ybr[y+j][x-1]
   440  		}
   441  	}
   442  }
   443  
   444  func predFunc8DCTop(z *Decoder, y, x int) {
   445  	sum := uint32(4)
   446  	for j := 0; j < 8; j++ {
   447  		sum += uint32(z.ybr[y+j][x-1])
   448  	}
   449  	avg := uint8(sum / 8)
   450  	for j := 0; j < 8; j++ {
   451  		for i := 0; i < 8; i++ {
   452  			z.ybr[y+j][x+i] = avg
   453  		}
   454  	}
   455  }
   456  
   457  func predFunc8DCLeft(z *Decoder, y, x int) {
   458  	sum := uint32(4)
   459  	for i := 0; i < 8; i++ {
   460  		sum += uint32(z.ybr[y-1][x+i])
   461  	}
   462  	avg := uint8(sum / 8)
   463  	for j := 0; j < 8; j++ {
   464  		for i := 0; i < 8; i++ {
   465  			z.ybr[y+j][x+i] = avg
   466  		}
   467  	}
   468  }
   469  
   470  func predFunc8DCTopLeft(z *Decoder, y, x int) {
   471  	for j := 0; j < 8; j++ {
   472  		for i := 0; i < 8; i++ {
   473  			z.ybr[y+j][x+i] = 0x80
   474  		}
   475  	}
   476  }
   477  
   478  func predFunc16DC(z *Decoder, y, x int) {
   479  	sum := uint32(16)
   480  	for i := 0; i < 16; i++ {
   481  		sum += uint32(z.ybr[y-1][x+i])
   482  	}
   483  	for j := 0; j < 16; j++ {
   484  		sum += uint32(z.ybr[y+j][x-1])
   485  	}
   486  	avg := uint8(sum / 32)
   487  	for j := 0; j < 16; j++ {
   488  		for i := 0; i < 16; i++ {
   489  			z.ybr[y+j][x+i] = avg
   490  		}
   491  	}
   492  }
   493  
   494  func predFunc16TM(z *Decoder, y, x int) {
   495  	delta0 := -int32(z.ybr[y-1][x-1])
   496  	for j := 0; j < 16; j++ {
   497  		delta1 := delta0 + int32(z.ybr[y+j][x-1])
   498  		for i := 0; i < 16; i++ {
   499  			delta2 := delta1 + int32(z.ybr[y-1][x+i])
   500  			z.ybr[y+j][x+i] = uint8(clip(delta2, 0, 255))
   501  		}
   502  	}
   503  }
   504  
   505  func predFunc16VE(z *Decoder, y, x int) {
   506  	for j := 0; j < 16; j++ {
   507  		for i := 0; i < 16; i++ {
   508  			z.ybr[y+j][x+i] = z.ybr[y-1][x+i]
   509  		}
   510  	}
   511  }
   512  
   513  func predFunc16HE(z *Decoder, y, x int) {
   514  	for j := 0; j < 16; j++ {
   515  		for i := 0; i < 16; i++ {
   516  			z.ybr[y+j][x+i] = z.ybr[y+j][x-1]
   517  		}
   518  	}
   519  }
   520  
   521  func predFunc16DCTop(z *Decoder, y, x int) {
   522  	sum := uint32(8)
   523  	for j := 0; j < 16; j++ {
   524  		sum += uint32(z.ybr[y+j][x-1])
   525  	}
   526  	avg := uint8(sum / 16)
   527  	for j := 0; j < 16; j++ {
   528  		for i := 0; i < 16; i++ {
   529  			z.ybr[y+j][x+i] = avg
   530  		}
   531  	}
   532  }
   533  
   534  func predFunc16DCLeft(z *Decoder, y, x int) {
   535  	sum := uint32(8)
   536  	for i := 0; i < 16; i++ {
   537  		sum += uint32(z.ybr[y-1][x+i])
   538  	}
   539  	avg := uint8(sum / 16)
   540  	for j := 0; j < 16; j++ {
   541  		for i := 0; i < 16; i++ {
   542  			z.ybr[y+j][x+i] = avg
   543  		}
   544  	}
   545  }
   546  
   547  func predFunc16DCTopLeft(z *Decoder, y, x int) {
   548  	for j := 0; j < 16; j++ {
   549  		for i := 0; i < 16; i++ {
   550  			z.ybr[y+j][x+i] = 0x80
   551  		}
   552  	}
   553  }
   554  

View as plain text