1 2/* 3 * Copyright 2009 The Android Open Source Project 4 * 5 * Use of this source code is governed by a BSD-style license that can be 6 * found in the LICENSE file. 7 */ 8 9 10#include "SkColorTable.h" 11#include "SkReadBuffer.h" 12#include "SkWriteBuffer.h" 13#include "SkStream.h" 14#include "SkTemplates.h" 15 16// As copy constructor is hidden in the class hierarchy, we need to call 17// default constructor explicitly to suppress a compiler warning. 18SkColorTable::SkColorTable(const SkColorTable& src) : INHERITED() { 19 f16BitCache = NULL; 20 fAlphaType = src.fAlphaType; 21 int count = src.count(); 22 fCount = SkToU16(count); 23 fColors = reinterpret_cast<SkPMColor*>( 24 sk_malloc_throw(count * sizeof(SkPMColor))); 25 memcpy(fColors, src.fColors, count * sizeof(SkPMColor)); 26 27 SkDEBUGCODE(fColorLockCount = 0;) 28 SkDEBUGCODE(f16BitCacheLockCount = 0;) 29} 30 31SkColorTable::SkColorTable(const SkPMColor colors[], int count, SkAlphaType at) 32 : f16BitCache(NULL), fAlphaType(SkToU8(at)) 33{ 34 SkASSERT(0 == count || colors); 35 36 if (count < 0) { 37 count = 0; 38 } else if (count > 256) { 39 count = 256; 40 } 41 42 fCount = SkToU16(count); 43 fColors = reinterpret_cast<SkPMColor*>( 44 sk_malloc_throw(count * sizeof(SkPMColor))); 45 46 memcpy(fColors, colors, count * sizeof(SkPMColor)); 47 48 SkDEBUGCODE(fColorLockCount = 0;) 49 SkDEBUGCODE(f16BitCacheLockCount = 0;) 50} 51 52SkColorTable::~SkColorTable() 53{ 54 SkASSERT(fColorLockCount == 0); 55 SkASSERT(f16BitCacheLockCount == 0); 56 57 sk_free(fColors); 58 sk_free(f16BitCache); 59} 60 61void SkColorTable::unlockColors() { 62 SkASSERT(fColorLockCount != 0); 63 SkDEBUGCODE(sk_atomic_dec(&fColorLockCount);) 64} 65 66#include "SkColorPriv.h" 67 68static inline void build_16bitcache(uint16_t dst[], const SkPMColor src[], 69 int count) { 70 while (--count >= 0) { 71 *dst++ = SkPixel32ToPixel16_ToU16(*src++); 72 } 73} 74 75const uint16_t* SkColorTable::lock16BitCache() { 76 if (this->isOpaque() && NULL == f16BitCache) { 77 f16BitCache = (uint16_t*)sk_malloc_throw(fCount * sizeof(uint16_t)); 78 build_16bitcache(f16BitCache, fColors, fCount); 79 } 80 81 SkDEBUGCODE(f16BitCacheLockCount += 1); 82 return f16BitCache; 83} 84 85/////////////////////////////////////////////////////////////////////////////// 86 87SkColorTable::SkColorTable(SkReadBuffer& buffer) { 88 f16BitCache = NULL; 89 SkDEBUGCODE(fColorLockCount = 0;) 90 SkDEBUGCODE(f16BitCacheLockCount = 0;) 91 92 fAlphaType = SkToU8(buffer.readUInt()); 93 fCount = buffer.getArrayCount(); 94 size_t allocSize = fCount * sizeof(SkPMColor); 95 SkDEBUGCODE(bool success = false;) 96 if (buffer.validateAvailable(allocSize)) { 97 fColors = (SkPMColor*)sk_malloc_throw(allocSize); 98 SkDEBUGCODE(success =) buffer.readColorArray(fColors, fCount); 99 } else { 100 fCount = 0; 101 fColors = NULL; 102 } 103#ifdef SK_DEBUG 104 SkASSERT((unsigned)fCount <= 256); 105 SkASSERT(success); 106#endif 107} 108 109void SkColorTable::writeToBuffer(SkWriteBuffer& buffer) const { 110 buffer.writeUInt(fAlphaType); 111 buffer.writeColorArray(fColors, fCount); 112} 113