void OSystem_Android::disableCursorPalette(bool disable) { ENTER("%d", disable); // when disabling the cursor palette, and we're running a clut8 game, // it expects the game palette to be used for the cursor if (disable && _game_texture->hasPalette()) { const byte *src = _game_texture->palette_const(); byte *dst = _mouse_texture_palette->palette(); const Graphics::PixelFormat &pf_src = _game_texture->getPalettePixelFormat(); const Graphics::PixelFormat &pf_dst = _mouse_texture_palette->getPalettePixelFormat(); uint8 r, g, b; for (uint i = 0; i < 256; ++i, src += 2, dst += 2) { pf_src.colorToRGB(READ_UINT16(src), r, g, b); WRITE_UINT16(dst, pf_dst.RGBToColor(r, g, b)); } byte *p = _mouse_texture_palette->palette() + _mouse_keycolor * 2; WRITE_UINT16(p, READ_UINT16(p) & ~1); } _use_mouse_palette = !disable; }
void RlfAnimation::decodeSimpleRunLengthEncoding(int8 *source, int8 *dest, uint32 sourceSize, uint32 destSize) const { uint32 sourceOffset = 0; uint32 destOffset = 0; int16 numberOfCopy = 0; while (sourceOffset < sourceSize) { int8 numberOfSamples = source[sourceOffset]; sourceOffset++; // If numberOfSamples is negative, the next abs(numberOfSamples) samples should // be copied directly from source to dest if (numberOfSamples < 0) { numberOfCopy = -numberOfSamples; while (numberOfCopy > 0) { if (sourceOffset + 1 >= sourceSize) { return; } else if (destOffset + 1 >= destSize) { debug(2, "Frame decoding overflow\n\tsourceOffset=%u\tsourceSize=%u\n\tdestOffset=%u\tdestSize=%u", sourceOffset, sourceSize, destOffset, destSize); return; } byte r, g, b; Graphics::colorToRGB<Graphics::ColorMasks<555> >(READ_LE_UINT16(source + sourceOffset), r, g, b); uint16 destColor = Graphics::RGBToColor<Graphics::ColorMasks<565> >(r, g, b); WRITE_UINT16(dest + destOffset, destColor); sourceOffset += 2; destOffset += 2; numberOfCopy--; } // If numberOfSamples is >= 0, copy one sample from source to the // next (numberOfSamples + 2) dest spots } else { if (sourceOffset + 1 >= sourceSize) { return; } byte r, g, b; Graphics::colorToRGB<Graphics::ColorMasks<555> >(READ_LE_UINT16(source + sourceOffset), r, g, b); uint16 sampleColor = Graphics::RGBToColor<Graphics::ColorMasks<565> >(r, g, b); sourceOffset += 2; numberOfCopy = numberOfSamples + 2; while (numberOfCopy > 0) { if (destOffset + 1 >= destSize) { debug(2, "Frame decoding overflow\n\tsourceOffset=%u\tsourceSize=%u\n\tdestOffset=%u\tdestSize=%u", sourceOffset, sourceSize, destOffset, destSize); return; } WRITE_UINT16(dest + destOffset, sampleColor); destOffset += 2; numberOfCopy--; } } } }
void Transport::nfcGetRecordData(size_t recordNumber, size_t item, size_t offset, uint8_t* data, size_t length) { uint8_t out[7]; WRITE_UINT16(&out[0], recordNumber); out[2] = item; WRITE_UINT16(&out[3], offset); WRITE_UINT16(&out[5], length); command(Transport::NFC_GET_RECORD_DATA, out, sizeof(out), data, length); }
void Transport::nfcSetRecordInfo(size_t recordNumber, uint16_t type, uint16_t* info, size_t infoCount) { uint8_t out[2+2+2*infoCount]; WRITE_UINT16(&out[0], recordNumber); WRITE_UINT16(&out[2], type); for(int i = 0; i < infoCount; i++) { WRITE_UINT16(&out[2+2+2*i], info[i]); } command(Transport::NFC_SET_RECORD_INFO, out, sizeof(out), NULL, 0); }
void OSystem_Android::setCursorPaletteInternal(const byte *colors, uint start, uint num) { const Graphics::PixelFormat &pf = _mouse_texture_palette->getPalettePixelFormat(); byte *p = _mouse_texture_palette->palette() + start * 2; for (uint i = 0; i < num; ++i, colors += 3, p += 2) WRITE_UINT16(p, pf.RGBToColor(colors[0], colors[1], colors[2])); p = _mouse_texture_palette->palette() + _mouse_keycolor * 2; WRITE_UINT16(p, READ_UINT16(p) & ~1); }
void Surface::scaleTransparentCopyGlow(const Common::Rect &srcRect, const Common::Rect &dstRect) const { // This is the same as scaleTransparentCopy(), but turns the red value of each // pixel all the way up. Graphics::Surface *screen = ((PegasusEngine *)g_engine)->_gfx->getCurSurface(); int srcW = srcRect.width(); int srcH = srcRect.height(); int dstW = dstRect.width(); int dstH = dstRect.height(); for (int y = 0; y < dstH; y++) { for (int x = 0; x < dstW; x++) { if (g_system->getScreenFormat().bytesPerPixel == 2) { uint16 color = READ_UINT16((byte *)_surface->getBasePtr( x * srcW / dstW + srcRect.left, y * srcH / dstH + srcRect.top)); if (!isTransparent(color)) WRITE_UINT16((byte *)screen->getBasePtr(x + dstRect.left, y + dstRect.top), getGlowColor(color)); } else if (g_system->getScreenFormat().bytesPerPixel == 4) { uint32 color = READ_UINT32((byte *)_surface->getBasePtr( x * srcW / dstW + srcRect.left, y * srcH / dstH + srcRect.top)); if (!isTransparent(color)) WRITE_UINT32((byte *)screen->getBasePtr(x + dstRect.left, y + dstRect.top), getGlowColor(color)); } } } }
void Surface::scaleTransparentCopy(const Common::Rect &srcRect, const Common::Rect &dstRect) const { // I'm doing simple linear scaling here // dstRect(x, y) = srcRect(x * srcW / dstW, y * srcH / dstH); Graphics::Surface *screen = ((PegasusEngine *)g_engine)->_gfx->getCurSurface(); int srcW = srcRect.width(); int srcH = srcRect.height(); int dstW = dstRect.width(); int dstH = dstRect.height(); for (int y = 0; y < dstH; y++) { for (int x = 0; x < dstW; x++) { if (g_system->getScreenFormat().bytesPerPixel == 2) { uint16 color = READ_UINT16((byte *)_surface->getBasePtr( x * srcW / dstW + srcRect.left, y * srcH / dstH + srcRect.top)); if (!isTransparent(color)) WRITE_UINT16((byte *)screen->getBasePtr(x + dstRect.left, y + dstRect.top), color); } else if (g_system->getScreenFormat().bytesPerPixel == 4) { uint32 color = READ_UINT32((byte *)_surface->getBasePtr( x * srcW / dstW + srcRect.left, y * srcH / dstH + srcRect.top)); if (!isTransparent(color)) WRITE_UINT32((byte *)screen->getBasePtr(x + dstRect.left, y + dstRect.top), color); } } } }
void Surface::copyToCurrentPortTransparentGlow(const Common::Rect &srcRect, const Common::Rect &dstRect) const { // This is the same as copyToCurrentPortTransparent(), but turns the red value of each // pixel all the way up. Graphics::Surface *screen = ((PegasusEngine *)g_engine)->_gfx->getCurSurface(); byte *src = (byte *)_surface->getBasePtr(srcRect.left, srcRect.top); byte *dst = (byte *)screen->getBasePtr(dstRect.left, dstRect.top); int lineSize = srcRect.width() * _surface->format.bytesPerPixel; for (int y = 0; y < srcRect.height(); y++) { for (int x = 0; x < srcRect.width(); x++) { if (g_system->getScreenFormat().bytesPerPixel == 2) { uint16 color = READ_UINT16(src); if (!isTransparent(color)) WRITE_UINT16(dst, getGlowColor(color)); } else if (g_system->getScreenFormat().bytesPerPixel == 4) { uint32 color = READ_UINT32(src); if (!isTransparent(color)) WRITE_UINT32(dst, getGlowColor(color)); } src += g_system->getScreenFormat().bytesPerPixel; dst += g_system->getScreenFormat().bytesPerPixel; } src += _surface->pitch - lineSize; dst += screen->pitch - lineSize; } }
/* FIXME: Should we abort or return error if the length and the field * size don't match? */ void pgp_put_header_length(struct nettle_buffer *buffer, /* start of the header */ unsigned start, unsigned field_size) { unsigned length; switch (field_size) { case 1: length = buffer->size - (start + 2); assert(length < PGP_LENGTH_TWO_OCTETS); buffer->contents[start + 1] = length; break; case 2: length = buffer->size - (start + 3); assert(length < PGP_LENGTH_FOUR_OCTETS && length >= PGP_LENGTH_TWO_OCTETS); WRITE_UINT16(buffer->contents + start + 1, length + LENGTH_TWO_OFFSET); break; case 4: length = buffer->size - (start + 5); WRITE_UINT32(buffer->contents + start + 2, length); break; default: abort(); } }
void dw_setPixel(SDL_Surface *s, Uint32 color, Uint16 x, Uint16 y) { assert(s); assert(x < s->w && y < s->h); Uint32 bpp = s->format->BytesPerPixel; Uint8 *p = (Uint8 *)s->pixels + (y * s->pitch) + (x * bpp); Uint32 pix; switch (bpp) { case 1: // b/w *p = color & 0xFF; break; case 2: // 16 bit per pixel WRITE_UINT16(p, color & 0xFFFF); break; case 3: WRITE_UINT32(&pix, color); p[0] = ((Uint8*)(&pix))[0]; p[1] = ((Uint8*)(&pix))[1]; p[2] = ((Uint8*)(&pix))[2]; break; case 4: WRITE_UINT32(p, color); break; default: // !?!? return; } }
int pgp_put_uint16(struct nettle_buffer *buffer, unsigned i) { uint8_t *p = nettle_buffer_space(buffer, 2); if (!p) return 0; WRITE_UINT16(p, i); return 1; }
void FlicDecoder::FlicVideoTrack::decodeDeltaFLC(uint8 *data) { uint16 linesInChunk = READ_LE_UINT16(data); data += 2; uint16 currentLine = 0; uint16 packetCount = 0; while (linesInChunk--) { uint16 opcode; // First process all the opcodes. do { opcode = READ_LE_UINT16(data); data += 2; switch ((opcode >> 14) & 3) { case OP_PACKETCOUNT: packetCount = opcode; break; case OP_UNDEFINED: break; case OP_LASTPIXEL: *((byte *)_surface->getBasePtr(getWidth() - 1, currentLine)) = (opcode & 0xFF); _dirtyRects.push_back(Common::Rect(getWidth() - 1, currentLine, getWidth(), currentLine + 1)); break; case OP_LINESKIPCOUNT: currentLine += -(int16)opcode; break; } } while (((opcode >> 14) & 3) != OP_PACKETCOUNT); uint16 column = 0; // Now interpret the RLE data while (packetCount--) { column += *data++; int rleCount = (int8)*data++; if (rleCount > 0) { memcpy((byte *)_surface->getBasePtr(column, currentLine), data, rleCount * 2); data += rleCount * 2; _dirtyRects.push_back(Common::Rect(column, currentLine, column + rleCount * 2, currentLine + 1)); } else if (rleCount < 0) { rleCount = -rleCount; uint16 dataWord = READ_UINT16(data); data += 2; for (int i = 0; i < rleCount; ++i) { WRITE_UINT16((byte *)_surface->getBasePtr(column + i * 2, currentLine), dataWord); } _dirtyRects.push_back(Common::Rect(column, currentLine, column + rleCount * 2, currentLine + 1)); } else { // End of cutscene ? return; } column += rleCount * 2; } currentLine++; } }
void Transport::nfcGetRecordInfo(size_t recordNumber, uint16_t* pType, uint16_t* info, size_t infoCount) { uint8_t out[2]; uint8_t in[2+2*infoCount]; WRITE_UINT16(&out[0], recordNumber); command(Transport::NFC_GET_RECORD_INFO, out, sizeof(out), in, sizeof(in)); READ_UINT16(&in[0], *pType); for(int i = 0; i < infoCount; i++) { READ_UINT16(&in[2+2*i], info[i]); } }
void Transport::nfcEncodePrefix(uint8_t* pPrefix, char* data, size_t dataLength) { uint8_t out[2 + dataLength]; uint8_t in[1]; WRITE_UINT16(&out[0], dataLength); memcpy(data, &out[2], dataLength); command(Transport::NFC_ENCODE_PREFIX, out, sizeof(out), in, sizeof(in)); *pPrefix = in[0]; }
void TinyGLBlit(byte *dst, byte *src, int x, int y, int width, int height, bool trans) { int srcPitch = width * 2; int dstPitch = 640 * 2; int srcX, srcY; int l, r; if (x > 639 || y > 479) return; if (x < 0) { srcX = -x; x = 0; } else { srcX = 0; } if (y < 0) { srcY = -y; y = 0; } else { srcY = 0; } if (x + width > 640) width -= (x + width) - 640; if (y + height > 480) height -= (y + height) - 480; dst += (x + (y * 640)) * 2; src += (srcX + (srcY * width)) * 2; int copyWidth = width * 2; if (!trans) { for (l = 0; l < height; l++) { memcpy(dst, src, copyWidth); dst += dstPitch; src += srcPitch; } } else { for (l = 0; l < height; l++) { for (r = 0; r < copyWidth; r += 2) { uint16 pixel = READ_UINT16(src + r); if (pixel != 0xf81f) WRITE_UINT16(dst + r, pixel); } dst += dstPitch; src += srcPitch; } } }
void RlfAnimation::decodeMaskedRunLengthEncoding(int8 *source, int8 *dest, uint32 sourceSize, uint32 destSize) const { uint32 sourceOffset = 0; uint32 destOffset = 0; int16 numberOfCopy = 0; while (sourceOffset < sourceSize) { int8 numberOfSamples = source[sourceOffset]; sourceOffset++; // If numberOfSamples is negative, the next abs(numberOfSamples) samples should // be copied directly from source to dest if (numberOfSamples < 0) { numberOfCopy = -numberOfSamples; while (numberOfCopy > 0) { if (sourceOffset + 1 >= sourceSize) { return; } else if (destOffset + 1 >= destSize) { debug(2, "Frame decoding overflow\n\tsourceOffset=%u\tsourceSize=%u\n\tdestOffset=%u\tdestSize=%u", sourceOffset, sourceSize, destOffset, destSize); return; } byte r, g, b; Graphics::colorToRGB<Graphics::ColorMasks<555> >(READ_LE_UINT16(source + sourceOffset), r, g, b); uint16 destColor = Graphics::RGBToColor<Graphics::ColorMasks<565> >(r, g, b); WRITE_UINT16(dest + destOffset, destColor); sourceOffset += 2; destOffset += 2; numberOfCopy--; } // If numberOfSamples is >= 0, move destOffset forward ((numberOfSamples * 2) + 2) // This function assumes the dest buffer has been memset with 0's. } else { if (sourceOffset + 1 >= sourceSize) { return; } else if (destOffset + 1 >= destSize) { debug(2, "Frame decoding overflow\n\tsourceOffset=%u\tsourceSize=%u\n\tdestOffset=%u\tdestSize=%u", sourceOffset, sourceSize, destOffset, destSize); return; } destOffset += (numberOfSamples * 2) + 2; } } }
void OSystem_Android::setPalette(const byte *colors, uint start, uint num) { ENTER("%p, %u, %u", colors, start, num); #ifdef USE_RGB_COLOR assert(_game_texture->hasPalette()); #endif GLTHREADCHECK; if (!_use_mouse_palette) setCursorPaletteInternal(colors, start, num); const Graphics::PixelFormat &pf = _game_texture->getPalettePixelFormat(); byte *p = _game_texture->palette() + start * 2; for (uint i = 0; i < num; ++i, colors += 3, p += 2) WRITE_UINT16(p, pf.RGBToColor(colors[0], colors[1], colors[2])); }
bool SaveConverter::swapDataEndian(byte *data, const byte *sizes, uint32 count) { if (!data || !sizes || (count == 0)) return false; while (count-- > 0) { if (*sizes == 3) // 32bit value (3 additional bytes) WRITE_UINT32(data, SWAP_BYTES_32(READ_UINT32(data))); else if (*sizes == 1) // 16bit value (1 additional byte) WRITE_UINT16(data, SWAP_BYTES_16(READ_UINT16(data))); else if (*sizes != 0) // else, it has to be an 8bit value return false; count -= *sizes; data += *sizes + 1; sizes += *sizes + 1; } return true; }
static void uncompressPlane(const byte *plane, byte *outptr, int length) { while (length != 0) { int wordlen; signed char x = *plane++; if (x >= 0) { wordlen = MIN<int>(x + 1, length); uint16 w = READ_UINT16(plane); plane += 2; for (int i = 0; i < wordlen; ++i) { WRITE_UINT16(outptr, w); outptr += 2; } } else { wordlen = MIN<int>(-x, length); memcpy(outptr, plane, wordlen * 2); outptr += wordlen * 2; plane += wordlen * 2; } length -= wordlen; } }
void MoviePlayer::copyFrameToBuffer(byte *dst, int dstType, uint x, uint y, uint pitch) { uint h = getHeight(); uint w = getWidth(); const Graphics::Surface *surface = decodeNextFrame(); byte *src = (byte *)surface->pixels; if (hasDirtyPalette()) _vm->setPaletteFromPtr(getPalette(), 256); if (_vm->_game.features & GF_16BIT_COLOR) { dst += y * pitch + x * 2; do { for (uint i = 0; i < w; i++) { uint16 color = READ_LE_UINT16(_vm->_hePalettes + _vm->_hePaletteSlot + 768 + src[i] * 2); switch (dstType) { case kDstScreen: WRITE_UINT16(dst + i * 2, color); break; case kDstResource: WRITE_LE_UINT16(dst + i * 2, color); break; default: error("copyFrameToBuffer: Unknown dstType %d", dstType); } } dst += pitch; src += w; } while (--h); } else { dst += y * pitch + x; do { memcpy(dst, src, w); dst += pitch; src += w; } while (--h); } }
void ScreenFader::setFaderValue(const int32 value) { if (value != getFaderValue()) { Fader::setFaderValue(value); if (_screen->getPixels()) { // The original game does a gamma fade here using the Mac API. In order to do // that, it would require an immense amount of CPU processing. This does a // linear fade instead, which looks fairly well, IMO. Graphics::Surface *screen = g_system->lockScreen(); for (uint y = 0; y < _screen->h; y++) { for (uint x = 0; x < _screen->w; x++) { if (_screen->format.bytesPerPixel == 2) WRITE_UINT16(screen->getBasePtr(x, y), fadePixel(READ_UINT16(_screen->getBasePtr(x, y)), value)); else WRITE_UINT32(screen->getBasePtr(x, y), fadePixel(READ_UINT32(_screen->getBasePtr(x, y)), value)); } } g_system->unlockScreen(); g_system->updateScreen(); } } }
/* FIXME: This function is a little ugly. It would get cleaner if we * just replaced the channel's receive function pointer with NULL on * failure and do_channel_forward_receive on success. */ static void do_client_channel_x11_receive(struct ssh_channel *s, int type, struct lsh_string *data) { CAST(client_x11_channel, self, s); if (type != CHANNEL_DATA) { werror("Ignoring unexpected stderr data.\n"); lsh_string_free(data); } else switch (self->state) { case CLIENT_X11_OK: A_WRITE(&self->super.socket->write_buffer->super, data); break; fail: channel_close(&self->super.super); self->state = CLIENT_X11_DENIED; break; case CLIENT_X11_DENIED: /* Any data on the channel should be stopped before we get * here; the CHANNEL_SENT_CLOSE should be set. */ fatal("Internal error!\n"); default: { /* Copy data to buffer */ UINT32 left = self->buffer->length - self->i; /* The small initial window size should ensure that we don't get * more data. */ assert(data->length <= left); memcpy(self->buffer->data + self->i, data->data, data->length); self->i += data->length; lsh_string_free(data); switch (self->state) { case CLIENT_X11_START: /* We need byte-order, major, minor and name_length, * which is 6 octets */ if (self->i < X11_SETUP_HEADER_LENGTH) break; self->state = CLIENT_X11_GOT_LENGTHS; switch (self->buffer->data[0]) { case 'B': /* Big endian */ case 'b': /* Big endian */ self->little_endian = 0; self->name_length = READ_UINT16(self->buffer->data + 6); self->auth_length = READ_UINT16(self->buffer->data + 8); break; case 'L': /* Little endian */ case 'l': /* Little endian */ self->little_endian = 1; self->name_length = LE_READ_UINT16(self->buffer->data + 6); self->auth_length = LE_READ_UINT16(self->buffer->data + 8); break; default: werror("client_x11.c: Bad endian indicator.\n"); goto fail; } if ( (self->name_length > 20) || (self->auth_length > 16) ) { werror("client_x11.c: Too long auth name or cookie\n"); goto fail; } /* Fall through */ case CLIENT_X11_GOT_LENGTHS: { const unsigned pad_length[4] = { 0, 3, 2, 1 }; #define PAD(l) (pad_length[ (l) % 4]) UINT32 auth_offset = X11_SETUP_HEADER_LENGTH + self->name_length + PAD(self->name_length); UINT32 length = auth_offset + self->auth_length + pad_length[self->auth_length % 4]; if (self->i < length) break; debug("Received cookie of type `%ps': %xs\n", self->name_length, self->buffer->data + X11_SETUP_HEADER_LENGTH, self->auth_length, self->buffer->data + auth_offset); /* Ok, now we have the connection setup message. Check if it's ok. */ if ( (self->name_length == MIT_COOKIE_NAME_LENGTH) && !memcmp(self->buffer->data + X11_SETUP_HEADER_LENGTH, MIT_COOKIE_NAME, MIT_COOKIE_NAME_LENGTH) && lsh_string_eq_l(self->display->fake, self->auth_length, self->buffer->data + auth_offset)) { struct lsh_string *msg; UINT8 lengths[4]; static const UINT8 pad[3] = { 0, 0, 0 }; /* Cookies match! */ verbose("client_x11: Allowing X11 connection; cookies match.\n"); if (self->little_endian) { LE_WRITE_UINT16(lengths, self->display->auth_name->length); LE_WRITE_UINT16(lengths + 2, self->display->auth_data->length); } else { WRITE_UINT16(lengths, self->display->auth_name->length); WRITE_UINT16(lengths + 2, self->display->auth_data->length); } /* FIXME: Perhaps it would be easier to build the message by hand than * using ssh_format? */ /* Construct the real setup message. */ msg = ssh_format("%ls%ls%c%c%ls%ls%ls%ls", X11_SETUP_VERSION_LENGTH, self->buffer->data, 4, lengths, 0, 0, self->display->auth_name->length, self->display->auth_name->data, PAD(self->display->auth_name->length), pad, self->display->auth_data->length, self->display->auth_data->data, self->i - length, self->buffer + self->i); lsh_string_free(self->buffer); self->buffer = NULL; /* Bump window size */ channel_start_receive(&self->super.super, X11_WINDOW_SIZE - msg->length); debug("client_x11.c: Sending real X11 setup message: %xS\n", msg); /* Send real x11 connection setup message. */ A_WRITE(&self->super.socket->write_buffer->super, msg); self->state = CLIENT_X11_OK; } else { werror("client_x11: X11 connection denied; bad cookie.\n"); goto fail; } break; #undef PAD } default: fatal("Internal error. do_client_channel_x11_receive"); break; } } break; } }
void ClassicCostumeRenderer::procPCEngine(Codec1 &v1) { const byte *mask, *src; byte *dst; byte maskbit; int xPos, yPos; uint pcolor, width, height; bool masked; int vertShift; int xStep; byte block[16][16]; src = _srcptr; width = _width / 16; height = _height / 16; if (_numBlocks == 0) return; xStep = _mirror ? +1 : -1; for (uint x = 0; x < width; ++x) { yPos = 0; for (uint y = 0; y < height; ++y) { vertShift = *src++; if (vertShift == 0xFF) { yPos += 16; continue; } else { yPos += vertShift; } memset(block, 0, sizeof(block)); int index = 0; while (index < 128) { byte cmd = *src++; int cnt = (cmd & 0x3F) + 1; if (!(cmd & 0xC0)) { for (int i = 0; i < cnt; ++i) PCESetCostumeData(block, index++, 0); } else if (cmd & 0x80) { int value = *src++; for (int i = 0; i < cnt; ++i) PCESetCostumeData(block, index++, value); } else { for (int i = 0; i < cnt; ++i) PCESetCostumeData(block, index++, *src++); } } if (index != 128) { warning("ClassicCostumeRenderer::procPCEngine: index %d != 128\n", index); } for (int row = 0; row < 16; ++row) { xPos = xStep * x * 16; for (int col = 0; col < 16; ++col) { dst = v1.destptr + yPos * _out.pitch + xPos * _vm->_bytesPerPixel; mask = v1.mask_ptr + yPos * _numStrips + (v1.x + xPos) / 8; maskbit = revBitMask((v1.x + xPos) % 8); pcolor = block[row][col]; masked = (v1.y + yPos < 0 || v1.y + yPos >= _out.h) || (v1.x + xPos < 0 || v1.x + xPos >= _out.w) || (v1.mask_ptr && (mask[0] & maskbit)); if (pcolor && !masked) { WRITE_UINT16(dst, ((uint16 *)_palette)[pcolor]); } xPos += xStep; } yPos++; } } } }
/* read bdf font bitmaps, return 0 on error*/ int bdf_read_bitmaps(Common::SeekableReadStream &fp, NewFontData* pf) { long ofs = 0; int maxwidth = 0; int i, k, encoding = 0, width = 0; int bbw = 0, bbh = 0, bbx = 0, bby = 0; int proportional = 0; int need_bbx = 0; int encodetable = 0; long l; char buf[256]; /* initially mark offsets as not used*/ for (i = 0; i < pf->size; ++i) pf->offset[i] = (unsigned long)-1; for (;;) { if (!bdf_getline(fp, buf, sizeof(buf))) { warning("Error: EOF on file"); return 0; } if (isprefix(buf, "STARTCHAR")) { encoding = width = bbw = bbh = bbx = bby = -1; continue; } if (isprefix(buf, "ENCODING ")) { if (sscanf(buf, "ENCODING %d", &encoding) != 1) { warning("Error: bad 'ENCODING'"); return 0; } if (encoding < start_char || encoding > limit_char) encoding = -1; continue; } if (isprefix(buf, "DWIDTH ")) { if (sscanf(buf, "DWIDTH %d", &width) != 1) { warning("Error: bad 'DWIDTH'"); return 0; } /* use font boundingbox width if DWIDTH <= 0*/ if (width <= 0) width = pf->fbbw - pf->fbbx; continue; } if (isprefix(buf, "BBX ")) { if (sscanf(buf, "BBX %d %d %d %d", &bbw, &bbh, &bbx, &bby) != 4) { warning("Error: bad 'BBX'"); return 0; } continue; } if (strequal(buf, "BITMAP")) { bitmap_t *ch_bitmap = pf->bits + ofs; int ch_words; if (encoding < 0) continue; /* set bits offset in encode map*/ if (pf->offset[encoding-pf->firstchar] != (unsigned long)-1) { warning("Error: duplicate encoding for character %d (0x%02x), ignoring duplicate", encoding, encoding); continue; } pf->offset[encoding-pf->firstchar] = ofs; pf->width[encoding-pf->firstchar] = width; pf->bbx[encoding-pf->firstchar].w = bbw; pf->bbx[encoding-pf->firstchar].h = bbh; pf->bbx[encoding-pf->firstchar].x = bbx; pf->bbx[encoding-pf->firstchar].y = bby; if (width > maxwidth) maxwidth = width; /* clear bitmap*/ memset(ch_bitmap, 0, BITMAP_BYTES(bbw) * bbh); ch_words = BITMAP_WORDS(bbw); /* read bitmaps*/ for (i = 0; i < bbh; ++i) { if (!bdf_getline(fp, buf, sizeof(buf))) { warning("Error: EOF reading BITMAP data"); return 0; } if (isprefix(buf, "ENDCHAR")) break; for (k = 0; k < ch_words; ++k) { bitmap_t value; value = bdf_hexval((unsigned char *)buf); if (bbw > 8) { WRITE_UINT16(ch_bitmap, value); } else { WRITE_UINT16(ch_bitmap, value << 8); } ch_bitmap++; } } ofs += ch_words * bbh; continue; } if (strequal(buf, "ENDFONT")) break; } /* set max width*/ pf->maxwidth = maxwidth; /* change unused offset/width values to default char values*/ for (i = 0; i < pf->size; ++i) { int defchar = pf->defaultchar - pf->firstchar; if (pf->offset[i] == (unsigned long)-1) { pf->offset[i] = pf->offset[defchar]; pf->width[i] = pf->width[defchar]; pf->bbx[i].w = pf->bbx[defchar].w; pf->bbx[i].h = pf->bbx[defchar].h; pf->bbx[i].x = pf->bbx[defchar].x; pf->bbx[i].y = pf->bbx[defchar].y; } } /* determine whether font doesn't require encode table*/ l = 0; for (i = 0; i < pf->size; ++i) { if (pf->offset[i] != (unsigned long)l) { encodetable = 1; break; } l += BITMAP_WORDS(pf->bbx[i].w) * pf->bbx[i].h; } if (!encodetable) { free(pf->offset); pf->offset = NULL; } /* determine whether font is fixed-width*/ for (i = 0; i < pf->size; ++i) { if (pf->width[i] != maxwidth) { proportional = 1; break; } } if (!proportional) { free(pf->width); pf->width = NULL; } /* determine if the font needs a bbx table */ for (i = 0; i < pf->size; ++i) { if (pf->bbx[i].w != pf->fbbw || pf->bbx[i].h != pf->fbbh || pf->bbx[i].x != pf->fbbx || pf->bbx[i].y != pf->fbby) { need_bbx = 1; break; } } if (!need_bbx) { free(pf->bbx); pf->bbx = NULL; } /* reallocate bits array to actual bits used*/ if (ofs < pf->bits_size) { bitmap_t *tmp = (bitmap_t *)realloc(pf->bits, ofs * sizeof(bitmap_t)); if (tmp != NULL || ofs == 0) pf->bits = tmp; else error("bdf_read_bitmaps: Error while reallocating memory"); pf->bits_size = ofs; } else { if (ofs > pf->bits_size) { warning("Warning: DWIDTH spec > max FONTBOUNDINGBOX"); if (ofs > pf->bits_size+EXTRA) { warning("Error: Not enough bits initially allocated"); return 0; } pf->bits_size = ofs; } } return 1; }
void Transport::nfcSetMessageInfo(size_t recordCount) { uint8_t out[2]; WRITE_UINT16(&out[0], recordCount); command(Transport::NFC_SET_MESSAGE_INFO, out, sizeof(out), NULL, 0); }
void OSystem_Android::setMouseCursor(const void *buf, uint w, uint h, int hotspotX, int hotspotY, uint32 keycolor, bool dontScale, const Graphics::PixelFormat *format) { ENTER("%p, %u, %u, %d, %d, %u, %d, %p", buf, w, h, hotspotX, hotspotY, keycolor, dontScale, format); GLTHREADCHECK; #ifdef USE_RGB_COLOR if (format && format->bytesPerPixel > 1) { if (_mouse_texture != _mouse_texture_rgb) { LOGD("switching to rgb mouse cursor"); assert(!_mouse_texture_rgb); _mouse_texture_rgb = new GLES5551Texture(); _mouse_texture_rgb->setLinearFilter(_graphicsMode == 1); } _mouse_texture = _mouse_texture_rgb; } else { if (_mouse_texture != _mouse_texture_palette) LOGD("switching to paletted mouse cursor"); _mouse_texture = _mouse_texture_palette; delete _mouse_texture_rgb; _mouse_texture_rgb = 0; } #endif _mouse_texture->allocBuffer(w, h); if (_mouse_texture == _mouse_texture_palette) { assert(keycolor < 256); byte *p = _mouse_texture_palette->palette() + _mouse_keycolor * 2; WRITE_UINT16(p, READ_UINT16(p) | 1); _mouse_keycolor = keycolor; p = _mouse_texture_palette->palette() + _mouse_keycolor * 2; WRITE_UINT16(p, READ_UINT16(p) & ~1); } if (w == 0 || h == 0) return; if (_mouse_texture == _mouse_texture_palette) { _mouse_texture->updateBuffer(0, 0, w, h, buf, w); } else { uint16 pitch = _mouse_texture->pitch(); byte *tmp = new byte[pitch * h]; // meh, a 16bit cursor without alpha bits... this is so silly if (!crossBlit(tmp, (const byte *)buf, pitch, w * 2, w, h, _mouse_texture->getPixelFormat(), *format)) { LOGE("crossblit failed"); delete[] tmp; _mouse_texture->allocBuffer(0, 0); return; } const uint16 *s = (const uint16 *)buf; uint16 *d = (uint16 *)tmp; for (uint16 y = 0; y < h; ++y, d += pitch / 2 - w) for (uint16 x = 0; x < w; ++x, d++) if (*s++ == (keycolor & 0xffff)) *d = 0; _mouse_texture->updateBuffer(0, 0, w, h, tmp, pitch); delete[] tmp; } _mouse_hotspot = Common::Point(hotspotX, hotspotY); // TODO: Adapt to the new "do not scale" cursor logic. _mouse_targetscale = 1; }
static void scaleThumbnail(Graphics::Surface &in, Graphics::Surface &out) { while (in.w / out.w >= 4 || in.h / out.h >= 4) { createThumbnail_4<565>((const uint8 *)in.getPixels(), in.pitch, (uint8 *)in.getPixels(), in.pitch, in.w, in.h); in.w /= 4; in.h /= 4; } while (in.w / out.w >= 2 || in.h / out.h >= 2) { createThumbnail_2<565>((const uint8 *)in.getPixels(), in.pitch, (uint8 *)in.getPixels(), in.pitch, in.w, in.h); in.w /= 2; in.h /= 2; } if ((in.w == out.w && in.h < out.h) || (in.w < out.w && in.h == out.h)) { // In this case we simply center the input surface in the output uint8 *dst = (uint8 *)out.getBasePtr((out.w - in.w) / 2, (out.h - in.h) / 2); const uint8 *src = (const uint8 *)in.getPixels(); for (int y = 0; y < in.h; ++y) { memcpy(dst, src, in.w * in.format.bytesPerPixel); src += in.pitch; dst += out.pitch; } } else { // Assure the aspect of the scaled image still matches the original. int targetWidth = out.w, targetHeight = out.h; const float inputAspect = (float)in.w / in.h; const float outputAspect = (float)out.w / out.h; if (inputAspect > outputAspect) { targetHeight = int(targetWidth / inputAspect); } else if (inputAspect < outputAspect) { targetWidth = int(targetHeight * inputAspect); } // Make sure we are still in the bounds of the output assert(targetWidth <= out.w); assert(targetHeight <= out.h); // Center the image on the output surface byte *dst = (byte *)out.getBasePtr((out.w - targetWidth) / 2, (out.h - targetHeight) / 2); const uint dstLineIncrease = out.pitch - targetWidth * out.format.bytesPerPixel; const float scaleFactorX = (float)targetWidth / in.w; const float scaleFactorY = (float)targetHeight / in.h; for (int y = 0; y < targetHeight; ++y) { const float yFrac = (y / scaleFactorY); const int y1 = (int)yFrac; const int y2 = (y1 + 1 < in.h) ? (y1 + 1) : (in.h - 1); for (int x = 0; x < targetWidth; ++x) { const float xFrac = (x / scaleFactorX); const int x1 = (int)xFrac; const int x2 = (x1 + 1 < in.w) ? (x1 + 1) : (in.w - 1); // Look up colors at the points uint8 p1R, p1G, p1B; Graphics::colorToRGB<Graphics::ColorMasks<565> >(READ_UINT16(in.getBasePtr(x1, y1)), p1R, p1G, p1B); uint8 p2R, p2G, p2B; Graphics::colorToRGB<Graphics::ColorMasks<565> >(READ_UINT16(in.getBasePtr(x2, y1)), p2R, p2G, p2B); uint8 p3R, p3G, p3B; Graphics::colorToRGB<Graphics::ColorMasks<565> >(READ_UINT16(in.getBasePtr(x1, y2)), p3R, p3G, p3B); uint8 p4R, p4G, p4B; Graphics::colorToRGB<Graphics::ColorMasks<565> >(READ_UINT16(in.getBasePtr(x2, y2)), p4R, p4G, p4B); const float xDiff = xFrac - x1; const float yDiff = yFrac - y1; uint8 pR = (uint8)((1 - yDiff) * ((1 - xDiff) * p1R + xDiff * p2R) + yDiff * ((1 - xDiff) * p3R + xDiff * p4R)); uint8 pG = (uint8)((1 - yDiff) * ((1 - xDiff) * p1G + xDiff * p2G) + yDiff * ((1 - xDiff) * p3G + xDiff * p4G)); uint8 pB = (uint8)((1 - yDiff) * ((1 - xDiff) * p1B + xDiff * p2B) + yDiff * ((1 - xDiff) * p3B + xDiff * p4B)); WRITE_UINT16(dst, Graphics::RGBToColor<Graphics::ColorMasks<565> >(pR, pG, pB)); dst += 2; } // Move to the next line dst = (byte *)dst + dstLineIncrease; } } }