void draw_frame(struct terminal *t, int x, int y, int xw, int yw, unsigned c, int w) { int *p = w > 1 ? p2 : p1; c |= ATTR_FRAME; set_char(t, x, y, c+p[0]); set_char(t, x+xw-1, y, c+p[1]); set_char(t, x, y+yw-1, c+p[2]); set_char(t, x+xw-1, y+yw-1, c+p[3]); fill_area(t, x, y+1, 1, yw-2, c+p[4]); fill_area(t, x+xw-1, y+1, 1, yw-2, c+p[4]); fill_area(t, x+1, y, xw-2, 1, c+p[5]); fill_area(t, x+1, y+yw-1, xw-2, 1, c+p[5]); }
void Pit::make_content_map() { assert(m_content_map.empty()); // leftover content map for(const auto& physical : m_contents) fill_area(*physical); }
static void run_test(void) { unsigned int i, j; for (i = 0; i < NR_CMDS; i++) { const struct alloc_cmd *cmd = &cmds[i]; if (cmd->size) { printk("ALLOC: %zu bytes marker=%d\n", cmd->size, cmd->marker); ptrs[i] = __alloc_percpu(cmd->size, __alignof__(unsigned long long)); if (ptrs[i]) fill_area(ptrs[i], cmd->size, i); else printk("failed to allocate %zu bytes\n", cmd->size); continue; } printk("FREE: marker=%d\n", cmd->marker); pcpu_dump_chunk_slots(); for (j = 0; j < i; j++) if (cmds[j].marker == cmd->marker) free_cmd(j); printk("FREE: done\n"); pcpu_dump_chunk_slots(); }
void Pit::fall_garbage(Garbage& garbage) { RowCol rc = garbage.rc(); RowCol to { rc.r+1, rc.c }; clear_area(garbage); garbage.set_rc(to); fill_area(garbage); }
Block& Pit::spawn_block(Block::Color color, RowCol rc, Block::State state) { enforce(rc.c >= 0); enforce(rc.c < PIT_COLS); auto block = std::make_unique<Block>(color, rc, state); Block* raw_block = block.get(); fill_area(*raw_block); m_contents.push_back(std::move(block)); if(rc.r < m_peak) m_peak = rc.r; return *raw_block; }
Garbage& Pit::spawn_garbage(RowCol rc, int width, int height) { // make sure the Garbage fits in the Pit enforce(rc.c >= 0); enforce(rc.c + width <= PIT_COLS); Loot loot(width * height); for(Block::Color& c : loot) c = m_color_supplier->next_emerge(); auto garbage = std::make_unique<Garbage>(rc, width, height, move(loot)); Garbage* raw_garbage = garbage.get(); fill_area(*raw_garbage); m_contents.push_back(std::move(garbage)); if(rc.r < m_peak) m_peak = rc.r; return *raw_garbage; }
static void reset_area() { fill_area(life,0,0,RESX+1,RESY+1,0); switch(pattern) { case 0: // R pentomino bitset_set2(life,41,40,1); bitset_set2(life,42,40,1); bitset_set2(life,41,41,1); bitset_set2(life,40,41,1); bitset_set2(life,41,42,1); break; case 1: // block in the center, continuous generators at the edges for(int i=0; i<RESX/2+3; ++i) bitset_set2(life,i,0,1); // for(int i=0; i<RESY; ++i) bitset_set2(life,0,i,1); // for(int i=0; i<RESY/2-20; ++i) bitset_set2(life,RESX+1,RESY-i,1); // for(int i=0; i<RESX/2; ++i) bitset_set2(life,RESX-i,RESY+1,1); bitset_set2(life,40,40,1); bitset_set2(life,41,40,1); bitset_set2(life,42,40,1); bitset_set2(life,42,41,1); bitset_set2(life,42,42,1); bitset_set2(life,40,41,1); bitset_set2(life,40,42,1); break; #if 0 case 2: // _|^|_ bitset_set2(life,40,40,1); bitset_set2(life,41,40,1); bitset_set2(life,42,40,1); bitset_set2(life,42,41,1); bitset_set2(life,42,42,1); bitset_set2(life,40,41,1); bitset_set2(life,40,42,1); break; #endif } }
int compare(Gif_Stream *s1, Gif_Stream *s2) { Gif_Colormap *newcm; int imageno1, imageno2, background1, background2; char buf1[256], buf2[256], fbuf[256]; was_different = 0; /* Compare image counts and screen sizes. If either of these differs, quit early. */ Gif_CalculateScreenSize(s1, 0); Gif_CalculateScreenSize(s2, 0); if (s1->nimages != s2->nimages && (s1->nimages == 0 || s2->nimages == 0)) { different("frame counts differ: <#%d >#%d", s1->nimages, s2->nimages); return DIFFERENT; } if (s1->screen_width != s2->screen_width || s1->screen_height != s2->screen_height) { different("screen sizes differ: <%dx%d >%dx%d", s1->screen_width, s1->screen_height, s2->screen_width, s2->screen_height); return DIFFERENT; } if (s1->screen_width == 0 || s1->screen_height == 0 || s2->screen_width == 0 || s2->screen_height == 0) { /* paranoia -- don't think this can happen */ different("zero screen sizes"); return DIFFERENT; } /* Create arrays for the image data */ screen_width = s1->screen_width; screen_height = s1->screen_height; gdata[0] = Gif_NewArray(uint16_t, screen_width * screen_height); gdata[1] = Gif_NewArray(uint16_t, screen_width * screen_height); glast[0] = Gif_NewArray(uint16_t, screen_width * screen_height); glast[1] = Gif_NewArray(uint16_t, screen_width * screen_height); scratch = Gif_NewArray(uint16_t, screen_width * screen_height); line = Gif_NewArray(uint16_t, screen_width); /* Merge all distinct colors from the two images into one colormap, setting the 'pixel' slots in the images' colormaps to the corresponding values in the merged colormap. Don't forget transparency */ newcm = Gif_NewFullColormap(1, 256); combine_colormaps(s1->global, newcm); combine_colormaps(s2->global, newcm); for (imageno1 = 0; imageno1 < s1->nimages; ++imageno1) combine_colormaps(s1->images[imageno1]->local, newcm); for (imageno2 = 0; imageno2 < s2->nimages; ++imageno2) combine_colormaps(s2->images[imageno2]->local, newcm); /* Choose the background values and clear the image data arrays */ if (s1->images[0]->transparent >= 0 || !s1->global) background1 = TRANSP; else background1 = s1->global->col[ s1->background ].pixel; if (s2->images[0]->transparent >= 0 || !s2->global) background2 = TRANSP; else background2 = s2->global->col[ s2->background ].pixel; fill_area(gdata[0], 0, 0, screen_width, screen_height, background1); fill_area(gdata[1], 0, 0, screen_width, screen_height, background2); /* Loopcounts differ? */ if (s1->loopcount != s2->loopcount) { name_loopcount(s1->loopcount, buf1); name_loopcount(s2->loopcount, buf2); different("loop counts differ: <%s >%s", buf1, buf2); } /* Loop over frames, comparing image data and delays */ apply_image(0, s1, 0, background1); apply_image(1, s2, 0, background2); imageno1 = imageno2 = 0; while (imageno1 != s1->nimages && imageno2 != s2->nimages) { int fi1 = imageno1, fi2 = imageno2, delay1 = s1->images[fi1]->delay, delay2 = s2->images[fi2]->delay; /* get message right */ if (imageno1 == imageno2) sprintf(fbuf, "#%d", imageno1); else sprintf(fbuf, "<#%d >#%d", imageno1, imageno2); /* compare pixels */ if (memcmp(gdata[0], gdata[1], screen_width * screen_height * sizeof(uint16_t)) != 0) { unsigned d, c = screen_width * screen_height; uint16_t *d1 = gdata[0], *d2 = gdata[1]; for (d = 0; d < c; d++, d1++, d2++) if (*d1 != *d2) { name_color(*d1, newcm, buf1); name_color(*d2, newcm, buf2); different("frame %s pixels differ: %d,%d <%s >%s", fbuf, d % screen_width, d / screen_width, buf1, buf2); break; } } /* move to next images, skipping redundancy */ for (++imageno1; imageno1 < s1->nimages && !apply_image(0, s1, imageno1, background1); ++imageno1) delay1 += s1->images[imageno1]->delay; for (++imageno2; imageno2 < s2->nimages && !apply_image(1, s2, imageno2, background2); ++imageno2) delay2 += s2->images[imageno2]->delay; if (!ignore_redundancy) { fi1 = (imageno1 - fi1) - (imageno2 - fi2); for (; fi1 > 0; --fi1) different("extra redundant frame: <#%d", imageno1 - fi1); for (; fi1 < 0; ++fi1) different("extra redundant frame: >#%d", imageno2 + fi1); } if (delay1 != delay2) { name_delay(delay1, buf1); name_delay(delay2, buf2); different("frame %s delays differ: <%s >%s", fbuf, buf1, buf2); } } if (imageno1 != s1->nimages || imageno2 != s2->nimages) different("frame counts differ: <#%d >#%d", s1->nimages, s2->nimages); /* That's it! */ Gif_DeleteColormap(newcm); Gif_DeleteArray(gdata[0]); Gif_DeleteArray(gdata[1]); Gif_DeleteArray(glast[0]); Gif_DeleteArray(glast[1]); Gif_DeleteArray(scratch); Gif_DeleteArray(line); return was_different ? DIFFERENT : SAME; }
static int apply_image(int is_second, Gif_Stream *gfs, int imageno, uint16_t background) { int i, x, y, any_change; Gif_Image *gfi = gfs->images[imageno]; Gif_Image *pgfi = imageno ? gfs->images[imageno - 1] : 0; int width = gfi->width; uint16_t map[256]; uint16_t *data = gdata[is_second]; uint16_t *last = glast[is_second]; Gif_Colormap *gfcm = gfi->local ? gfi->local : gfs->global; /* set up colormap */ for (i = 0; i < 256; i++) map[i] = 1; if (gfs) for (i = 0; i < gfcm->ncol; i++) map[i] = gfcm->col[i].pixel; if (gfi->transparent >= 0 && gfi->transparent < 256) map[gfi->transparent] = TRANSP; /* if this image's disposal is 'previous', save the post-disposal version in 'scratch' */ if (gfi->disposal == GIF_DISPOSAL_PREVIOUS) { copy_area(scratch, data, gfi->left, gfi->top, gfi->width, gfi->height); if (pgfi && pgfi->disposal == GIF_DISPOSAL_PREVIOUS) copy_area(scratch, last, pgfi->left, pgfi->top, pgfi->width, pgfi->height); else if (pgfi && pgfi->disposal == GIF_DISPOSAL_BACKGROUND) fill_area(scratch, pgfi->left, pgfi->top, pgfi->width, pgfi->height, background); } /* uncompress and clip */ Gif_UncompressImage(gfs, gfi); Gif_ClipImage(gfi, 0, 0, screen_width, screen_height); any_change = imageno == 0; { int lf = 0, tp = 0, rt = 0, bt = 0; expand_bounds(&lf, &tp, &rt, &bt, gfi); if (pgfi && pgfi->disposal == GIF_DISPOSAL_PREVIOUS) expand_bounds(&lf, &tp, &rt, &bt, pgfi); else if (pgfi && pgfi->disposal == GIF_DISPOSAL_BACKGROUND) { expand_bounds(&lf, &tp, &rt, &bt, pgfi); fill_area(last, pgfi->left, pgfi->top, pgfi->width, pgfi->height, background); } else pgfi = 0; for (y = tp; y < bt; ++y) { uint16_t *outd = data + screen_width * y + lf; if (!any_change) memcpy(line, outd, (rt - lf) * sizeof(uint16_t)); if (pgfi && y >= pgfi->top && y < pgfi->top + pgfi->height) memcpy(outd + pgfi->left - lf, last + screen_width * y + pgfi->left, pgfi->width * sizeof(uint16_t)); if (y >= gfi->top && y < gfi->top + gfi->height) { uint16_t *xoutd = outd + gfi->left - lf; const uint8_t *ind = gfi->img[y - gfi->top]; for (x = 0; x < width; ++x, ++ind, ++xoutd) if (map[*ind] != TRANSP) *xoutd = map[*ind]; } if (!any_change && memcmp(line, outd, (rt - lf) * sizeof(uint16_t)) != 0) any_change = 1; } } Gif_ReleaseUncompressedImage(gfi); Gif_ReleaseCompressedImage(gfi); /* switch 'glast' with 'scratch' if necessary */ if (gfi->disposal == GIF_DISPOSAL_PREVIOUS) { uint16_t *x = scratch; scratch = glast[is_second]; glast[is_second] = x; } return any_change; }
void Blob2D::resize(short destLeft, short destTop, short destWidth, short destHeight) { if( width == 0 && height == 0) { size_t siz = Bitmap::size(destWidth,destHeight); if( alloc_size < siz ) { if(ptr) mem_del(ptr); ptr = (Bitmap *)mem_add((alloc_size = siz + DEFAULT_BLOB2D_INC)); } memset(ptr, BACKGROUND_COLOR, siz); ptr->init(destWidth, destHeight); } else if( destWidth == 0 && destHeight == 0 ) { err_when(!ptr); ptr->init(destWidth, destHeight); } else if( left_edge == destLeft && top_edge == destTop && width == destWidth ) { if( destHeight == height ) return; // unchange size_t siz = Bitmap::size(destWidth,destHeight); if( alloc_size < siz ) { ptr = (Bitmap *)mem_resize(ptr, (alloc_size = siz + DEFAULT_BLOB2D_INC)); } if( destHeight > height && destWidth > 0 ) { int y2 = top_edge+height; // must keep the old instant height = destHeight; // as height must be change to make fill_area correct // extend, then fill the new with the background color fill_area(destLeft, top_edge+height, destLeft+destWidth-1, destTop+destHeight-1, BACKGROUND_COLOR, 0); } } else if( left_edge <= destLeft && top_edge <= destTop && left_edge+width >= destLeft+destWidth && top_edge+height >= destTop+destHeight) { // clipping unsigned char *src = ptr->get_ptr(destLeft-left_edge, destTop-top_edge); int srcPitch = ptr->get_pitch(); ptr->init(destWidth, destHeight); unsigned char *dest = ptr->get_ptr(); int destPitch = ptr->get_pitch(); for(int y = 0; y < destHeight; ++y, src += srcPitch, dest += destPitch ) memmove(dest, src, destWidth); // ptr = (Bitmap *)mem_resize(ptr, ptr->size()); } else { // general resize, new another buffer // copy range, intersection of two area : short copyLeft, copyTop, copyWidth, copyHeight; copyLeft = max(destLeft, left_edge); copyTop = max(destTop, top_edge); copyWidth = min(destLeft + destWidth, left_edge + width) - copyLeft; copyHeight = min(destTop + destHeight, top_edge + height) - copyTop; { size_t siz = Bitmap::size(destWidth, destHeight); Bitmap *newPtr = (Bitmap *)mem_add(siz + DEFAULT_BLOB2D_INC); memset(newPtr, BACKGROUND_COLOR, siz); newPtr->init(destWidth, destHeight); if( copyWidth > 0 && copyHeight > 0 ) { int yCount = 0; unsigned char *src = ptr->get_ptr(copyLeft-left_edge, yCount+copyTop-top_edge ); unsigned char *dest = newPtr->get_ptr(copyLeft-destLeft, yCount+copyTop-destTop ); for( ; yCount < copyHeight; ++yCount, src += ptr->get_pitch(), dest += ptr->get_pitch() ) { // unsigned char *src = (yCount+copyTop-top_edge)*width + copyLeft-left_edge; // unsigned char *dest = (yCount+copyTop-destTop)*destWdith + copyLeft-destLeft; memcpy(dest, src, copyWidth); } } // assign to the newPtr now left_edge = destLeft; top_edge = destTop; width = destWidth; height = destHeight; if(ptr) mem_del(ptr); ptr = newPtr; } // fill rest area with background color if( top_edge < copyTop && width > 0) { fill_area(left_edge, top_edge, left_edge+width-1, copyTop, BACKGROUND_COLOR, 0 ); } // fill bottom if( top_edge+height > copyTop+copyHeight && width > 0) { fill_area(left_edge, copyTop+copyHeight, left_edge+width-1, top_edge+height-1, BACKGROUND_COLOR, 0 ); } // fill left if( left_edge < copyLeft && destHeight > 0) { fill_area(left_edge, copyTop, copyLeft-1, copyTop+copyHeight-1, BACKGROUND_COLOR, 0); } // fill right if( left_edge+width > copyLeft+copyWidth && destHeight > 0 ) { fill_area(copyLeft+copyWidth, copyTop, left_edge+width, copyTop+copyHeight-1, BACKGROUND_COLOR, 0); } } left_edge = destLeft; top_edge = destTop; width = destWidth; height = destHeight; }
void clear_terminal(struct terminal *term) { fill_area(term, 0, 0, term->x, term->y, ' '); set_cursor(term, 0, 0, 0, 0); }