src/hbcore/svgext/hbnvgdecoder/hbnvgcsicon.cpp
changeset 0 16d8024aca5e
child 1 f7ac710697a9
equal deleted inserted replaced
-1:000000000000 0:16d8024aca5e
       
     1 /****************************************************************************
       
     2 **
       
     3 ** Copyright (C) 2008-2010 Nokia Corporation and/or its subsidiary(-ies).
       
     4 ** All rights reserved.
       
     5 ** Contact: Nokia Corporation (developer.feedback@nokia.com)
       
     6 **
       
     7 ** This file is part of the HbCore module of the UI Extensions for Mobile.
       
     8 **
       
     9 ** GNU Lesser General Public License Usage
       
    10 ** This file may be used under the terms of the GNU Lesser General Public
       
    11 ** License version 2.1 as published by the Free Software Foundation and
       
    12 ** appearing in the file LICENSE.LGPL included in the packaging of this file.
       
    13 ** Please review the following information to ensure the GNU Lesser General
       
    14 ** Public License version 2.1 requirements will be met:
       
    15 ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
       
    16 **
       
    17 ** In addition, as a special exception, Nokia gives you certain additional
       
    18 ** rights.  These rights are described in the Nokia Qt LGPL Exception
       
    19 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
       
    20 **
       
    21 ** If you have questions regarding the use of this file, please contact
       
    22 ** Nokia at developer.feedback@nokia.com.
       
    23 **
       
    24 ****************************************************************************/
       
    25 
       
    26 #include "hbnvgcsicon_p.h"
       
    27 #include "hbnvgicondata_p.h"
       
    28 #include "hbnvgfittoviewbox_p.h"
       
    29 #include "hbnvgutil_p.h"
       
    30 #include "hbopenvghandlestore_p.h"
       
    31 #include "hbnvgexception_p.h"
       
    32 
       
    33 #include <QScopedPointer>
       
    34 #include <QScopedArrayPointer>
       
    35 
       
    36 /*!
       
    37   NVG-CS version
       
    38  */
       
    39 const int Version2   = 2;
       
    40 
       
    41 /*!
       
    42   File offsets
       
    43  */
       
    44 const int NVG_VIEWBOX_WIDTH_OFS = 44;
       
    45 const int NVG_VIEWBOX_HEIGHT_OFS = 48;
       
    46 const int NVG_VIEWBOX_X_OFS = 36;
       
    47 const int NVG_VIEWBOX_Y_OFS = 40;
       
    48 const int NVG_PATHDATATYPE_OFS = 26;
       
    49 const int NVG_SCALE_OFS = 28;
       
    50 const int NVG_BIAS_OFS = 32;
       
    51 const int NVG_COMMANDSECTION_OFS = 2;
       
    52 const int NVG_RGBA_OFS = 4;
       
    53 const int NVG_HEADERSIZE_OFS = 4;
       
    54 const int NVG_PAINTSECTION_LINEARGRAD_TRANSFORM_OFFSET = 20;
       
    55 const int NVG_PAINTSECTION_RADIALGRAD_TRANSFORM_OFFSET = 24;
       
    56 const int NVG_VERSION_OFS         = 3;
       
    57 
       
    58 /*!
       
    59   NVG-CS commands
       
    60  */ 
       
    61 const int CMD_SET_FILL_PAINT           = 4  << 24;
       
    62 const int CMD_SET_COLOR_RAMP           = 6  << 24;
       
    63 const int CMD_DRAW_PATH                = 7  << 24;
       
    64 const int CMD_SET_TRANSFORMATION       = 8  << 24;
       
    65 const int CMD_SET_STROKE_PAINT         = 5  << 24;
       
    66 const int CMD_SET_STROKE_WIDTH         = 9  << 24;
       
    67 const int CMD_SET_STROKE_LINE_JOIN_CAP = 10 << 24;
       
    68 const int CMD_SET_STROKE_MITER_LIMIT   = 11 << 24;
       
    69 
       
    70 /*!
       
    71  Stroke cap style
       
    72  */
       
    73 const int CAP_BUTT        = 1;
       
    74 const int CAP_SQUARE      = 2;
       
    75 const int CAP_ROUND       = 3;
       
    76 
       
    77 /*!
       
    78  Stroke join style
       
    79  */
       
    80 const int LINE_JOIN_BEVEL = 1;
       
    81 const int LINE_JOIN_MITER = 2;
       
    82 const int LINE_JOIN_ROUND = 3;
       
    83 
       
    84 /*!
       
    85  Fill paint type
       
    86  */
       
    87 const int PAINT_FLAT      = 1;
       
    88 const int PAINT_LGRAD     = 2;
       
    89 const int PAINT_RGRAD     = 3;
       
    90 
       
    91 /*!
       
    92  Stroke paint type
       
    93  */
       
    94 const int STROKE_LGRAD        = 2;
       
    95 const int STROKE_RGRAD        = 3;
       
    96 const int STROKE_COLOR_RAMP   = 4;
       
    97 
       
    98 /*!
       
    99  Transform encoding values
       
   100  */
       
   101 const int TRANSFORM_COMPLETE    = 0;
       
   102 const int TRANSFORM_SCALING     = 2;
       
   103 const int TRANSFORM_SHEARING    = 4;
       
   104 const int TRANSFORM_ROTATION    = 8;
       
   105 const int TRANSFORM_TRANSLATION = 16;
       
   106 
       
   107 const VGfloat IdentityMatrix[] = {
       
   108     1.0f, 0.0f, 0.0f,
       
   109     0.0f, 1.0f, 0.0f,
       
   110     0.0f, 0.0f , 1.0f
       
   111 };
       
   112 
       
   113     /**
       
   114      * @fn      Constructor
       
   115      * @Version
       
   116      * @parameter: buffer - None
       
   117      *
       
   118      * @return: None
       
   119      */
       
   120 
       
   121 HbNvgCsIcon::HbNvgCsIcon()
       
   122         :   mPaintFill(VG_INVALID_HANDLE),
       
   123         mPaintStroke(VG_INVALID_HANDLE),
       
   124         mVgPath(VG_INVALID_HANDLE),
       
   125         mLastPathDataType(0),
       
   126         mDoFill (VG_FALSE),
       
   127         mDoStroke(VG_FALSE),
       
   128         mCreatingNvgIcon(0),
       
   129         mPreserveAspectSetting(HbNvgEngine::NvgPreserveAspectRatioXmidYmid),
       
   130         mSmilFitSetting(HbNvgEngine::NvgMeet),
       
   131         mNvgIconData(0),
       
   132         mOpenVgHandles(0),
       
   133         mLastFillPaintType(0),
       
   134         mLastStrokePaintType(0),
       
   135         mLastFillPaintColor(0),
       
   136         mLastStrkePaintColor(0),
       
   137         mResetFillPaint(0),
       
   138         mResetStrokePaint(0),
       
   139         mMirroringMode(false)
       
   140 {
       
   141 }
       
   142 
       
   143 void HbNvgCsIcon::setIconData(const QByteArray &buffer)
       
   144 {
       
   145     mNvgIconData = new HbNvgIconData(buffer.size());
       
   146     Q_CHECK_PTR(mNvgIconData);
       
   147     mOpenVgHandles = new HbOpenVgHandleStore();
       
   148     Q_CHECK_PTR(mNvgIconData);
       
   149 }
       
   150 
       
   151 HbNvgCsIcon::~HbNvgCsIcon()
       
   152 {
       
   153     if (mPaintFill) {
       
   154         vgDestroyPaint(mPaintFill);
       
   155     }
       
   156     if (mPaintStroke) {
       
   157         vgDestroyPaint(mPaintStroke);
       
   158     }
       
   159     if (mVgPath) {
       
   160         vgDestroyPath(mVgPath);
       
   161     }
       
   162     
       
   163     vgSetPaint(VG_INVALID_HANDLE, VG_FILL_PATH);
       
   164     vgSetPaint(VG_INVALID_HANDLE, VG_STROKE_PATH);
       
   165     
       
   166     delete mNvgIconData;
       
   167     delete mOpenVgHandles;
       
   168 }
       
   169 
       
   170 
       
   171 void HbNvgCsIcon::setViewBox(float x, float y, float w, float h)
       
   172 {
       
   173     mViewBoxX = x;
       
   174     mViewBoxY = y;
       
   175     mViewBoxW = w;
       
   176     mViewBoxH = h;
       
   177 }
       
   178 
       
   179 void  HbNvgCsIcon::setPreserveAspectRatio(HbNvgEngine::NvgAlignStatusType preserveAspectSetting,
       
   180         HbNvgEngine::NvgMeetOrSliceType smilFitSetting)
       
   181 {
       
   182     mPreserveAspectSetting = preserveAspectSetting;
       
   183     mSmilFitSetting = smilFitSetting;
       
   184 }
       
   185 
       
   186 void HbNvgCsIcon::setMirroringMode(bool mirroringMode)
       
   187 {
       
   188     mMirroringMode = mirroringMode;
       
   189 }
       
   190 
       
   191 void HbNvgCsIcon::rotate(float angle, float xValue, float yValue)
       
   192 {
       
   193      mRotationAngle  = angle;
       
   194      mRotationX      = xValue;
       
   195      mRotationY      = yValue;
       
   196 }
       
   197 
       
   198 void HbNvgCsIcon ::directDraw(const QByteArray &buffer, const QSize &targetSize)
       
   199 {
       
   200     drawCommandSection(buffer, targetSize, 0);
       
   201 }
       
   202 
       
   203 void HbNvgCsIcon::create(const QByteArray &buffer, const QSize& targetSize)
       
   204 {
       
   205     drawCommandSection(buffer, targetSize, 1);
       
   206 }
       
   207 
       
   208 void HbNvgCsIcon::drawCommandSection(const QByteArray &buffer, const QSize & targetSize,
       
   209         int objectCaching)
       
   210 {       
       
   211     mCreatingNvgIcon = objectCaching;
       
   212  
       
   213     HbDereferencer iconData(buffer);
       
   214     qint16 lHeaderSize  = iconData.derefInt16(NVG_HEADERSIZE_OFS);
       
   215     quint8 nvgVersion   = iconData.derefInt8(NVG_VERSION_OFS);
       
   216  
       
   217     HbNvgEngine::NvgErrorType errInit = HbNvgEngine::NvgErrNone;
       
   218         
       
   219     errInit = initializeGc();
       
   220     if (HbNvgEngine::NvgErrNone != errInit){
       
   221        throw HbNvgException(errInit);
       
   222     }
       
   223         
       
   224     qint16 lPathDataType = iconData.derefInt16(NVG_PATHDATATYPE_OFS);
       
   225     float lScale         = iconData.derefReal32(NVG_SCALE_OFS);
       
   226     float lBias          = iconData.derefReal32(NVG_BIAS_OFS);
       
   227 
       
   228     errInit = createPathHandle(lPathDataType, lScale, lBias);
       
   229     if (HbNvgEngine::NvgErrNone != errInit){
       
   230         throw HbNvgException(errInit);
       
   231     }
       
   232 
       
   233     VGfloat lCurrentPathMatrix[9];
       
   234     vgGetMatrix(lCurrentPathMatrix);
       
   235     vgSeti(VG_MATRIX_MODE, VG_MATRIX_PATH_USER_TO_SURFACE);
       
   236 
       
   237     // We use the caller's base batrix regardless of which mode the caller was.
       
   238     // The caller may have set the matrix in VG_MATRIX_IMAGE_USER_TO_SURFACE mode
       
   239     // as it thinks it is drawing images (textures).
       
   240     // But even though the texture gets stroked instead, we must use the caller's
       
   241     // transformation matrix.
       
   242     // Everything gets restored to the original values before we return.
       
   243     vgLoadMatrix(lCurrentPathMatrix);
       
   244 
       
   245 //    applyScissoring(lCurrentPathMatrix, targetSize);
       
   246 
       
   247     /*
       
   248      * set the rotation angle if available
       
   249      */
       
   250            
       
   251     setRotation();
       
   252     
       
   253     if (mMirroringMode) {
       
   254 	    vgTranslate((VGfloat)(targetSize.width()), 0); 
       
   255 	    vgScale(-1.0f, 1.0f);
       
   256 	    }
       
   257     
       
   258 
       
   259 #ifdef __MIRROR_
       
   260      vgScale(1.0f, -1.0f);
       
   261      vgTranslate(0, (VGfloat)(-targetSize.height()));
       
   262 #endif
       
   263 
       
   264     //viewbox parameters
       
   265     float lViewboxX   = iconData.derefReal32(NVG_VIEWBOX_X_OFS);
       
   266     float lViewboxY   = iconData.derefReal32(NVG_VIEWBOX_Y_OFS);
       
   267     float lViewboxW   = iconData.derefReal32(NVG_VIEWBOX_WIDTH_OFS);
       
   268     float lViewboxH   = iconData.derefReal32(NVG_VIEWBOX_HEIGHT_OFS);
       
   269 
       
   270     applyViewboxToViewPortTransformation(targetSize, lViewboxX, lViewboxY, lViewboxW, lViewboxH);
       
   271 
       
   272     quint32 offsetSectionLength = iconData.getLength() - lHeaderSize;
       
   273     quint8 * offsetPtr = iconData.derefInt8Array(offsetSectionLength, lHeaderSize);
       
   274     
       
   275     HbDereferencer offsetSection(offsetPtr, offsetSectionLength);
       
   276     quint16 lOffsetVectorCount = offsetSection.derefInt16();
       
   277 
       
   278     offsetPtr = iconData.derefInt8Array(offsetSectionLength - sizeof(quint16), lHeaderSize + sizeof(quint16));
       
   279     HbDereferencer offsetVector(offsetPtr, offsetSectionLength - sizeof(quint16));
       
   280 
       
   281     qint32 commandSectionOffset = lOffsetVectorCount * sizeof(quint16);
       
   282     HbDereferencer commandSection((offsetVector.getPtr() + commandSectionOffset), 
       
   283             iconData.getLength() - commandSectionOffset - lHeaderSize - sizeof(quint16));
       
   284             
       
   285     // from version 2 onwards command section will start on word boundary
       
   286     if (nvgVersion >= Version2 && ((lOffsetVectorCount  & 0x01) == 0))
       
   287         {
       
   288         commandSection.skip(2);
       
   289         }
       
   290          
       
   291     quint16 lCmdCount = commandSection.derefInt16();
       
   292     commandSection.skip(NVG_COMMANDSECTION_OFS);   
       
   293     
       
   294     /*
       
   295      * from version 2 onwards there will be a padding added
       
   296      * after the command count to make it word aligned
       
   297      */
       
   298     if (nvgVersion >= Version2)
       
   299         {
       
   300         commandSection.skip(2);
       
   301         }
       
   302         
       
   303     executeNVGCSCommandLoop(lCmdCount, &iconData, &offsetVector, &commandSection, nvgVersion);
       
   304 }
       
   305 
       
   306 void HbNvgCsIcon::executeNVGCSCommandLoop(quint16 commandCount, HbDereferencer *iconData, 
       
   307         HbDereferencer * offsetVector,HbDereferencer * commandSection, quint8 nvgVersion)
       
   308     {
       
   309     quint32 transVal;
       
   310 
       
   311     VGfloat lCurrentPathMatrix[9];
       
   312     
       
   313     vgGetMatrix(lCurrentPathMatrix);
       
   314         
       
   315     qint32 lOffsetIx = 0;
       
   316     for (int i=0; i < commandCount; i++)
       
   317         {
       
   318         quint32 currentCommand = commandSection->derefInt32();
       
   319         lOffsetIx = currentCommand & 0x0000ffff;
       
   320                 
       
   321         switch (currentCommand & 0xff000000)
       
   322             {
       
   323             case CMD_SET_FILL_PAINT:
       
   324                 {
       
   325                 mFillAlpha        = (currentCommand & 0x00ff0000) >> 16;
       
   326                 quint16 offset    = offsetVector->derefInt16(lOffsetIx * sizeof(quint16));
       
   327                 
       
   328                 HbDereferencer section = getCommandSection(offset, iconData, nvgVersion);
       
   329                                 
       
   330                 setFillPaint(&section); 
       
   331                 }
       
   332                 break;    
       
   333             case CMD_SET_COLOR_RAMP:
       
   334                 {
       
   335                 quint16 offset = offsetVector->derefInt16(lOffsetIx * sizeof(quint16));
       
   336 
       
   337                 HbDereferencer section = getCommandSection(offset, iconData, nvgVersion);
       
   338 
       
   339                 setColorRamp(&section);
       
   340                 }
       
   341                 break;
       
   342             case CMD_DRAW_PATH:
       
   343                 {
       
   344                 if ((currentCommand & 0x00010000)) 
       
   345                     {
       
   346                     mDoStroke = VG_TRUE;
       
   347                     }
       
   348                 
       
   349                 if ((currentCommand & 0x00020000))
       
   350                     {
       
   351                     mDoFill = VG_TRUE;
       
   352                     }
       
   353                 quint16 offset = offsetVector->derefInt16(lOffsetIx * sizeof(quint16));
       
   354 
       
   355                 HbDereferencer section = getCommandSection(offset, iconData, nvgVersion);
       
   356 
       
   357                 drawPath(&section);
       
   358                 }
       
   359                 break;
       
   360             case CMD_SET_TRANSFORMATION:
       
   361                 {
       
   362                 setTransform(commandSection, transVal, lCurrentPathMatrix);
       
   363                 commandSection->skip(transVal * sizeof(quint32));
       
   364                 }
       
   365                 break;
       
   366             case CMD_SET_STROKE_PAINT:
       
   367                 {
       
   368                 mStrokeAlpha = (currentCommand & 0x00ff0000) >> 16;
       
   369                 quint16 offset = offsetVector->derefInt16(lOffsetIx * sizeof(quint16));
       
   370 
       
   371                 HbDereferencer section = getCommandSection(offset, iconData, nvgVersion);
       
   372 
       
   373                 setStrokePaint(&section); 
       
   374                 }
       
   375                 break;
       
   376             case CMD_SET_STROKE_WIDTH:
       
   377                 {
       
   378                 float lStrokeWidth;
       
   379                 commandSection->skip(sizeof(quint32));
       
   380                 
       
   381                 /*
       
   382                  * check for alignment and copy data if not aligned, else directly convert
       
   383                  * version 2 or above guarantees that is always word aligned
       
   384                  */
       
   385                 quint8 * cptr = commandSection->derefInt8Array(sizeof(float), 0); 
       
   386                 if (nvgVersion < Version2 && !isAligned4(cptr))
       
   387                     {
       
   388                     
       
   389                     memcpy(reinterpret_cast<void *>(&lStrokeWidth),
       
   390                               reinterpret_cast<void *>(cptr), sizeof(lStrokeWidth));
       
   391                     }
       
   392                 else
       
   393                     {
       
   394                     lStrokeWidth = commandSection->derefReal32();
       
   395                     }
       
   396                 
       
   397                 COND_COM_OC(mCreatingNvgIcon,
       
   398                         addSetStrokeWidthCommand(lStrokeWidth),
       
   399                         vgSetf(VG_STROKE_LINE_WIDTH, lStrokeWidth));
       
   400                 }
       
   401                 break;
       
   402             case CMD_SET_STROKE_MITER_LIMIT:
       
   403                 {
       
   404                 float lMiterLimit;
       
   405                 commandSection->skip(sizeof(float));
       
   406 
       
   407                 /*
       
   408                  * check for alignment and copy data if not aligned, else directly convert
       
   409                  * version 2 or above guarantees that is always word aligned
       
   410                  */
       
   411                 quint8 * cptr = commandSection->derefInt8Array(sizeof(float), 0); 
       
   412 
       
   413                 if (nvgVersion < Version2 && !isAligned4(cptr))
       
   414                     {
       
   415                     memcpy(reinterpret_cast<void *>(&lMiterLimit),
       
   416                               reinterpret_cast<void *>(cptr), sizeof(lMiterLimit));
       
   417                     }
       
   418                 else
       
   419                     {
       
   420                     lMiterLimit = commandSection->derefReal32();
       
   421                     }
       
   422                 
       
   423                 COND_COM_OC(mCreatingNvgIcon,
       
   424                         addSetStrokeMiterLimitCommand(lMiterLimit),
       
   425                         vgSetf(VG_STROKE_MITER_LIMIT, lMiterLimit));
       
   426                 }
       
   427                 break;
       
   428             case CMD_SET_STROKE_LINE_JOIN_CAP:
       
   429                 {
       
   430                 quint8 lJoinType =(currentCommand & 0x0000ff00)>>8;
       
   431                 quint8 lCapType = (currentCommand & 0x000000ff);
       
   432                 
       
   433                 VGCapStyle capStyle;
       
   434                 switch(lCapType)
       
   435                     {
       
   436                     case CAP_SQUARE:
       
   437                         capStyle = VG_CAP_SQUARE;
       
   438                         break;
       
   439                     case CAP_ROUND:
       
   440                         capStyle = VG_CAP_ROUND;
       
   441                         break;
       
   442                     case CAP_BUTT:
       
   443                     default:
       
   444                         capStyle = VG_CAP_BUTT;
       
   445                         break;
       
   446                     }
       
   447    
       
   448                 VGJoinStyle lineJoinStyle;
       
   449                 switch(lJoinType)
       
   450                     {
       
   451                     case LINE_JOIN_BEVEL:
       
   452                         lineJoinStyle = VG_JOIN_BEVEL;
       
   453                         break;
       
   454                     case LINE_JOIN_ROUND:
       
   455                         lineJoinStyle = VG_JOIN_ROUND;
       
   456                         break;
       
   457                     case LINE_JOIN_MITER:
       
   458                     default:
       
   459                         lineJoinStyle = VG_JOIN_MITER;
       
   460                         break;
       
   461                     }
       
   462                 
       
   463                 COND_COM_OC(mCreatingNvgIcon,
       
   464                         addStrokeLineJoinCapCommand(capStyle, lineJoinStyle),
       
   465                         vgSeti(VG_STROKE_CAP_STYLE, capStyle);
       
   466                         vgSeti(VG_STROKE_JOIN_STYLE, lineJoinStyle););
       
   467                 }
       
   468                 break;
       
   469             default:
       
   470                 {
       
   471                 throw HbNvgException(HbNvgEngine::NvgErrCorrupt);			
       
   472                 }
       
   473             }
       
   474         
       
   475         // go to the next command
       
   476         commandSection->skip(sizeof(quint32));
       
   477         }
       
   478     
       
   479     }
       
   480 
       
   481 HbDereferencer HbNvgCsIcon::getCommandSection(quint16 offset, HbDereferencer * iconData, int nvgVersion)
       
   482     {
       
   483     // the max length that the command section can have
       
   484     int commandSectionLength = iconData->getLength() - offset;
       
   485 
       
   486     if (commandSectionLength <= 0){
       
   487         throw HbNvgException(HbNvgEngine::NvgErrCorrupt);
       
   488     }
       
   489 
       
   490     HbDereferencer section(iconData->derefInt8Array(commandSectionLength, offset), commandSectionLength);
       
   491 
       
   492     /*
       
   493      * all the section are expected to be word aligned
       
   494      * all of the nvg-cs icon will be version 2 or above
       
   495      * the else won't be there as nvg version will always be greater than 2
       
   496      */
       
   497     if (nvgVersion >= Version2) {
       
   498         if (!isAligned4(offset)) {
       
   499             throw HbNvgException(HbNvgEngine::NvgErrCorrupt);
       
   500         }
       
   501     }else{
       
   502         /*
       
   503          * no need to do anything here as once the nvgdecoder release
       
   504          * its version will be always greater than 2
       
   505          * infact the check for version will be removed
       
   506          */ 
       
   507     }
       
   508     
       
   509     return section;
       
   510     }
       
   511 
       
   512 void HbNvgCsIcon::applyViewboxToViewPortTransformation(const QSize& targetSize, 
       
   513         float viewboxX, float viewboxY, float viewboxW, float viewboxH)
       
   514     {
       
   515     HbNvgFitToViewBoxImpl *viewBoxTx = new HbNvgFitToViewBoxImpl();
       
   516     Q_CHECK_PTR(viewBoxTx);
       
   517     QScopedPointer<HbNvgFitToViewBoxImpl> viewboxTrnsfr(viewBoxTx);
       
   518 
       
   519     /*
       
   520      * this is bit unreadable,
       
   521      * need to find a better design to separate the object caching solution from normal rendering,
       
   522      */
       
   523     
       
   524     COND_COM_OC_NOC(
       
   525             {
       
   526             if (mCreatingNvgIcon) {
       
   527                 setViewBox(viewboxX, viewboxY, viewboxW, viewboxH);
       
   528                 }
       
   529             else{
       
   530                 viewboxTrnsfr->setAlign(mPreserveAspectSetting);
       
   531                 viewboxTrnsfr->setScaling(mSmilFitSetting);
       
   532                 
       
   533                 if (viewboxW > 0 && viewboxH > 0){
       
   534                     viewboxTrnsfr->setViewBox(viewboxX, viewboxY, viewboxW, viewboxH);
       
   535                 }
       
   536                 
       
   537                 int lWidth = aTargetSize.width();
       
   538                 int lHeight = aTargetSize.height();
       
   539                 
       
   540                 viewboxTrnsfr->setWindowViewportTrans(QRect(0, 0, lWidth, lHeight), QSize(0, 0));
       
   541             }
       
   542            },
       
   543             {
       
   544             viewboxTrnsfr->setAlign(mPreserveAspectSetting);
       
   545             viewboxTrnsfr->setScaling(mSmilFitSetting);
       
   546             
       
   547             if (viewboxW > 0 && viewboxH > 0){
       
   548                 viewboxTrnsfr->setViewBox(viewboxX, viewboxY, viewboxW, viewboxH);
       
   549                 }
       
   550             
       
   551             int lWidth = targetSize.width();
       
   552             int lHeight = targetSize.height();
       
   553             
       
   554             viewboxTrnsfr->setWindowViewportTrans(QRect(0, 0, lWidth, lHeight), QSize(0, 0));
       
   555             });
       
   556     }
       
   557 
       
   558 void HbNvgCsIcon::applyScissoring(VGfloat *aMatrix, const QSize& targetSize)
       
   559     {
       
   560     /*
       
   561      * calculate the rectangle with respect to the transformation applied
       
   562      * and set the scissoring rect
       
   563      */ 
       
   564     QPoint leftBottom  = getTranslatedPoint(aMatrix, QPoint(0, 0));
       
   565     QPoint leftTop     = getTranslatedPoint(aMatrix, QPoint(0, targetSize.height()));
       
   566     QPoint rightBottom = getTranslatedPoint(aMatrix, QPoint(targetSize.width(), 0));
       
   567     QPoint rightTop    = getTranslatedPoint(aMatrix, QPoint(targetSize.width(),targetSize.height()));
       
   568 
       
   569     VGfloat minX = leftBottom.x();
       
   570     VGfloat minY = leftBottom.y();
       
   571     VGfloat maxX = leftBottom.x();
       
   572     VGfloat maxY = leftBottom.y();
       
   573 
       
   574     minX = minVal4(leftBottom.x(), leftTop.x(), rightBottom.x(), rightTop.x());
       
   575     minY = minVal4(leftBottom.y(), leftTop.y(), rightBottom.y(), rightTop.y());
       
   576 
       
   577     maxX = maxVal4(leftBottom.x(), leftTop.x(), rightBottom.x(), rightTop.x());
       
   578     maxY = maxVal4(leftBottom.y(), leftTop.y(), rightBottom.y(), rightTop.y());
       
   579 
       
   580     VGfloat newW = maxX - minX;
       
   581     VGfloat newH = maxY - minY;
       
   582 
       
   583     VGint clipRect[] = {minX, minY, newW, newH};
       
   584 
       
   585     vgSeti(VG_SCISSORING, VG_TRUE);
       
   586     vgSetiv(VG_SCISSOR_RECTS, 4, clipRect);
       
   587     }
       
   588 
       
   589 
       
   590 HbNvgEngine::NvgErrorType HbNvgCsIcon::initializeGc()
       
   591 {
       
   592     if (mPaintFill == VG_INVALID_HANDLE) {
       
   593         mPaintFill = vgCreatePaint();
       
   594         if (mPaintFill == VG_INVALID_HANDLE) {
       
   595             return openVgErrorToHbNvgError(vgGetError());
       
   596         }
       
   597     }
       
   598     
       
   599     vgSetPaint(mPaintFill, VG_FILL_PATH);
       
   600     
       
   601     if (mPaintStroke == VG_INVALID_HANDLE) {
       
   602         mPaintStroke = vgCreatePaint();
       
   603         if (mPaintStroke == VG_INVALID_HANDLE) {
       
   604             return openVgErrorToHbNvgError(vgGetError());
       
   605         }
       
   606     }
       
   607 
       
   608     vgSetPaint(mPaintStroke, VG_STROKE_PATH);
       
   609 
       
   610     return HbNvgEngine::NvgErrNone;
       
   611 }
       
   612 
       
   613 HbNvgEngine::NvgErrorType HbNvgCsIcon::createPathHandle(qint16 pathDataType, float scale, float bias)
       
   614 {
       
   615     (void) scale;
       
   616     (void) bias;
       
   617 
       
   618     HbNvgEngine::NvgErrorType error = HbNvgEngine::NvgErrNone;
       
   619 
       
   620     if (mLastPathDataType != pathDataType) {
       
   621         if (mVgPath != VG_INVALID_HANDLE) {
       
   622             vgDestroyPath(mVgPath);
       
   623             mVgPath = VG_INVALID_HANDLE;
       
   624         }
       
   625     }
       
   626 
       
   627     if (mVgPath == VG_INVALID_HANDLE) {
       
   628         switch (pathDataType) {
       
   629         case NvgEightBitEncoding: {
       
   630             mVgPath = vgCreatePath(VG_PATH_FORMAT_STANDARD,
       
   631                                    VG_PATH_DATATYPE_S_16, 1.0f / 2.0f, 0.0f, 0, 0,
       
   632                                    VG_PATH_CAPABILITY_APPEND_TO);
       
   633             break;
       
   634             }
       
   635             
       
   636         case NvgSixteenBitEncoding: {
       
   637             mVgPath = vgCreatePath(VG_PATH_FORMAT_STANDARD,
       
   638                                    VG_PATH_DATATYPE_S_16, 1.0f / 16.0f, 0.0f, 0, 0,
       
   639                                    VG_PATH_CAPABILITY_APPEND_TO);
       
   640             break;
       
   641             }
       
   642             
       
   643         case NvgThirtyTwoBitEncoding: {
       
   644             mVgPath = vgCreatePath(VG_PATH_FORMAT_STANDARD,
       
   645                                    VG_PATH_DATATYPE_S_32, 1.0f / 65536.0f, 0.0f, 0, 0,
       
   646                                    VG_PATH_CAPABILITY_APPEND_TO);
       
   647             break;
       
   648             }
       
   649 
       
   650         default: {
       
   651             return HbNvgEngine::NvgErrCorrupt;
       
   652             }
       
   653         }
       
   654     }
       
   655 
       
   656     if (mVgPath == VG_INVALID_HANDLE) {
       
   657         // Get the Symbian error code
       
   658         error = openVgErrorToHbNvgError(vgGetError());
       
   659 
       
   660         if (error == HbNvgEngine::NvgErrNoMemory) {
       
   661             NVG_DEBUGP1("NVG Error OOMs: vgCreatePaint");
       
   662             resetNvgState();
       
   663         }
       
   664 
       
   665         NVG_DEBUGP1("NVG Error: vgCreatePaint");
       
   666         return error;
       
   667     }
       
   668 
       
   669     mLastPathDataType   = pathDataType;
       
   670 
       
   671     return error;
       
   672 }
       
   673 
       
   674 void HbNvgCsIcon::resetNvgState()
       
   675 {
       
   676     if (mVgPath != VG_INVALID_HANDLE) {
       
   677         vgDestroyPath(mVgPath);
       
   678         mVgPath = VG_INVALID_HANDLE;
       
   679     }
       
   680 
       
   681     if (mPaintFill != VG_INVALID_HANDLE) {
       
   682         vgSetPaint(VG_INVALID_HANDLE, VG_FILL_PATH);
       
   683         vgDestroyPaint(mPaintFill);
       
   684         mPaintFill = VG_INVALID_HANDLE;
       
   685     }
       
   686 
       
   687     if (mPaintStroke != VG_INVALID_HANDLE) {
       
   688         vgSetPaint(VG_INVALID_HANDLE, VG_STROKE_PATH);
       
   689         vgDestroyPaint(mPaintStroke);
       
   690         mPaintStroke = VG_INVALID_HANDLE;
       
   691     }
       
   692 }
       
   693 
       
   694     /**
       
   695      * @fn setFillPaint
       
   696      * @brief  SetPaint gradient or solid in OpenVG
       
   697      * @version
       
   698      * @param   buffer - buffer containing OpenVG data
       
   699      * @return  None
       
   700      */
       
   701 
       
   702 void HbNvgCsIcon::setFillPaint(HbDereferencer *iconData)
       
   703 {
       
   704     COND_COM_OC_OOC(register int drawingMode = mCreatingNvgIcon);
       
   705     
       
   706     quint32 lCommonData  = iconData->derefInt32();
       
   707     quint32 lPaintType   = lCommonData & 0x07;
       
   708     quint16 lSpecifcData = (lCommonData >> 16) & 0xff;
       
   709 
       
   710     switch (lPaintType) {
       
   711         case PAINT_LGRAD: {
       
   712             mGradPaintFill = mPaintFill;
       
   713             COND_COM_OC_OOC(
       
   714                 if (mCreatingNvgIcon) {
       
   715                 // CNVGCSIcon will destroy the paint handle
       
   716                 mGradPaintFill = vgCreatePaint();
       
   717                 if (mGradPaintFill == VG_INVALID_HANDLE){
       
   718                     throw HbNvgException(openVgErrorToHbNvgError(vgGetError()));
       
   719                 }
       
   720             });
       
   721 
       
   722             // gradient data, the data will be word aligned
       
   723             float* lGradData =  (float*)iconData->derefInt8Array(4 * sizeof(VGfloat), sizeof(float));
       
   724             
       
   725             vgSetParameteri(mGradPaintFill, VG_PAINT_TYPE, VG_PAINT_TYPE_LINEAR_GRADIENT);
       
   726             vgSetParameterfv(mGradPaintFill, VG_PAINT_LINEAR_GRADIENT, 4, lGradData);
       
   727             vgSeti(VG_MATRIX_MODE, VG_MATRIX_FILL_PAINT_TO_USER);
       
   728 
       
   729             if (lSpecifcData & 0x1) {
       
   730                 float* lGradMatrix1 = (float*) iconData->derefInt8Array(6 * sizeof (VGfloat),
       
   731                                                                    NVG_PAINTSECTION_LINEARGRAD_TRANSFORM_OFFSET);
       
   732                                
       
   733                 float lGradMatrix[9] = {lGradMatrix1[0], lGradMatrix1[3], 0.0f,
       
   734                                         lGradMatrix1[1], lGradMatrix1[4], 0.0f,
       
   735                                         lGradMatrix1[2], lGradMatrix1[5], 1.0f
       
   736                                        };
       
   737     
       
   738                 COND_COM_OC(drawingMode,
       
   739                             addLinearGradientCommand(4, lGradData, lGradMatrix, mGradPaintFill),
       
   740                             vgLoadMatrix(lGradMatrix););
       
   741                 Q_UNUSED(IdentityMatrix);
       
   742             } else {
       
   743                 COND_COM_OC(drawingMode,
       
   744                             addLinearGradientCommand(4, lGradData, (VGfloat*)IdentityMatrix, mGradPaintFill),
       
   745                             vgLoadIdentity());
       
   746             }
       
   747 
       
   748             COND_COM_OC(drawingMode, ; ,
       
   749                         vgSeti(VG_MATRIX_MODE, VG_MATRIX_PATH_USER_TO_SURFACE));
       
   750         }
       
   751         break;
       
   752         case PAINT_RGRAD: {
       
   753             mGradPaintFill = mPaintFill;
       
   754     
       
   755             COND_COM_OC_OOC(
       
   756             if (mCreatingNvgIcon) {
       
   757                 mGradPaintFill = vgCreatePaint();
       
   758                 if (mGradPaintFill == VG_INVALID_HANDLE){
       
   759                     throw HbNvgException(openVgErrorToHbNvgError(vgGetError()));
       
   760                 }                
       
   761             });
       
   762     
       
   763             // gradient data, the data will be word aligned
       
   764             float* lGradData = (float*)iconData->derefInt8Array(4 * sizeof(VGfloat), sizeof(quint32));
       
   765                        
       
   766             vgSetParameteri(mGradPaintFill, VG_PAINT_TYPE, VG_PAINT_TYPE_RADIAL_GRADIENT);
       
   767             vgSetParameterfv(mGradPaintFill, VG_PAINT_RADIAL_GRADIENT, 5, lGradData);
       
   768             vgSeti(VG_MATRIX_MODE, VG_MATRIX_FILL_PAINT_TO_USER);
       
   769     
       
   770     
       
   771             if (lSpecifcData & 0x1) {
       
   772                 float* lGradMatrix1 = (float*)iconData->derefInt8Array(6 * sizeof (VGfloat),
       
   773                                         NVG_PAINTSECTION_RADIALGRAD_TRANSFORM_OFFSET);
       
   774                 float lGradMatrix[9] = {lGradMatrix1[0], lGradMatrix1[3], 0.0f,
       
   775                                         lGradMatrix1[1], lGradMatrix1[4], 0.0f,
       
   776                                         lGradMatrix1[2], lGradMatrix1[5], 1.0f
       
   777                                        };
       
   778     
       
   779                 COND_COM_OC(drawingMode,
       
   780                             addRadialGradientCommand(5, lGradData, lGradMatrix, mGradPaintFill),
       
   781                             vgLoadMatrix(lGradMatrix));
       
   782                 Q_UNUSED(IdentityMatrix);
       
   783             } else {
       
   784                 COND_COM_OC(drawingMode,
       
   785                             addRadialGradientCommand(5, lGradData, (VGfloat*)IdentityMatrix, mGradPaintFill),
       
   786                             vgLoadIdentity());
       
   787             }
       
   788     
       
   789             COND_COM_OC(drawingMode, ; ,
       
   790                         vgSeti(VG_MATRIX_MODE, VG_MATRIX_PATH_USER_TO_SURFACE));
       
   791         }
       
   792         break;
       
   793         case PAINT_FLAT:
       
   794             {
       
   795             quint32 lRgba = iconData->derefInt32(NVG_RGBA_OFS);
       
   796     
       
   797             lRgba = (lRgba & 0xffffff00) | mFillAlpha;
       
   798             
       
   799             COND_COM_OC(drawingMode,
       
   800                     addSetColorCommand(lRgba),
       
   801                     vgSetParameteri(mPaintFill, VG_PAINT_TYPE, VG_PAINT_TYPE_COLOR);
       
   802                     vgSetColor(mPaintFill, lRgba));            
       
   803             }
       
   804             break;
       
   805         default: {
       
   806             throw HbNvgException(HbNvgEngine::NvgErrCorrupt);
       
   807         }
       
   808     }
       
   809 }
       
   810 
       
   811 void HbNvgCsIcon::setColorRamp(HbDereferencer *iconData)
       
   812 {
       
   813     quint32 lCommonData = iconData->derefInt32();
       
   814 
       
   815     int lStopCount = (lCommonData >> 16) & 0x00ff;
       
   816     float* lStopData = (float*) iconData->derefInt8Array(lStopCount * 5 * sizeof(float), sizeof(quint32));
       
   817     
       
   818     VGfloat *crs = new VGfloat[lStopCount * 5];
       
   819     Q_CHECK_PTR(crs);
       
   820     QScopedArrayPointer<VGfloat> colorRamps(crs); 
       
   821     
       
   822     if (mFillAlpha == 0xff) {
       
   823         vgSetParameteri(mGradPaintFill, VG_PAINT_COLOR_RAMP_SPREAD_MODE, VG_COLOR_RAMP_SPREAD_PAD);
       
   824         vgSetParameterfv(mGradPaintFill, VG_PAINT_COLOR_RAMP_STOPS, lStopCount*5, lStopData);
       
   825     } else {
       
   826         // Copy color ramps and modify alpha
       
   827         memcpy(colorRamps.data(), lStopData, lStopCount*5*sizeof(VGfloat));
       
   828         VGfloat lAlphaInFloat = mFillAlpha * 0.003921568627450f; //(1.0f/255.0f);
       
   829         VGfloat* lAlphaValue = &(colorRamps[4]);
       
   830         for (int i = 0; i < lStopCount; i++) {
       
   831             *lAlphaValue *= lAlphaInFloat;
       
   832             lAlphaValue += 5;
       
   833         }
       
   834 
       
   835         vgSetParameteri(mGradPaintFill, VG_PAINT_COLOR_RAMP_SPREAD_MODE, VG_COLOR_RAMP_SPREAD_PAD);
       
   836         vgSetParameterfv(mGradPaintFill, VG_PAINT_COLOR_RAMP_STOPS, lStopCount * 5, colorRamps.data());
       
   837     }
       
   838 }
       
   839 
       
   840 void HbNvgCsIcon::drawPath(HbDereferencer * iconData)
       
   841 {
       
   842     int numSegments = iconData->derefInt16();
       
   843     const VGubyte * pathSegments  = iconData->derefInt8Array(numSegments, sizeof(quint16));
       
   844     /*
       
   845     * verify that what we got is proper data
       
   846     * for that calculate the path co-ordinate length
       
   847     * and check that the path data does not overflow
       
   848     */    
       
   849    int coordinateCount = 0;
       
   850    for (int i = 0; i < numSegments; ++i)
       
   851        {
       
   852        switch (pathSegments[i])
       
   853            {
       
   854            case VG_HLINE_TO:
       
   855            case VG_VLINE_TO:
       
   856                coordinateCount += 1;
       
   857                break;
       
   858            case VG_MOVE_TO:
       
   859            case VG_LINE_TO:
       
   860            case VG_SQUAD_TO:
       
   861                coordinateCount += 2;
       
   862                break;                
       
   863            case VG_QUAD_TO:
       
   864            case VG_SCUBIC_TO:
       
   865                coordinateCount += 4;
       
   866                break;
       
   867            case VG_SCCWARC_TO:
       
   868            case VG_SCWARC_TO:
       
   869            case VG_LCCWARC_TO:
       
   870            case VG_LCWARC_TO:
       
   871                coordinateCount += 5;
       
   872                break;
       
   873            case VG_CUBIC_TO:
       
   874                coordinateCount += 6;
       
   875                break;
       
   876            default:
       
   877                break;
       
   878            }
       
   879        }
       
   880 
       
   881    // this one is just to check the alignment
       
   882    quint8* pathData = iconData->derefInt8Array(sizeof(float), sizeof(quint16) + numSegments);
       
   883    
       
   884    /*
       
   885     * path data need to be word aligned
       
   886     * alignment are done according to the path format
       
   887     */
       
   888    quint32 sizeofpathdata = sizeof(float);
       
   889    quint32 alignSkip = 0;
       
   890    quint8 * alignedPtr = 0;
       
   891    if (mLastPathDataType == NvgSixteenBitEncoding)
       
   892        {
       
   893        alignedPtr = Align2(pathData);
       
   894        sizeofpathdata = sizeof( quint16);
       
   895        }
       
   896    else if (mLastPathDataType == NvgThirtyTwoBitEncoding)
       
   897        {        
       
   898        alignedPtr = Align4(pathData);
       
   899        }
       
   900    else
       
   901        {
       
   902        throw HbNvgException(HbNvgEngine::NvgErrCorrupt);
       
   903        }
       
   904    
       
   905    alignSkip = alignedPtr - pathData; 
       
   906    
       
   907    /*
       
   908     * check to see whether we have enough path data
       
   909     */
       
   910    iconData->isSafe(coordinateCount * sizeofpathdata + alignSkip, sizeof(quint16) + numSegments);
       
   911    
       
   912    pathData = alignedPtr;
       
   913    
       
   914    VGint paintMode = (mDoFill ? VG_FILL_PATH : 0)|(mDoStroke ? VG_STROKE_PATH : 0);
       
   915    if (paintMode == 0)
       
   916        {
       
   917        paintMode = VG_FILL_PATH;
       
   918        }
       
   919    
       
   920    COND_COM_OC(mCreatingNvgIcon,
       
   921            {
       
   922                VGPath path = createPath();
       
   923                
       
   924                if (path != VG_INVALID_HANDLE)
       
   925                    {
       
   926                    vgAppendPathData(path, numSegments, pathSegments, pathData);
       
   927                    }
       
   928                else
       
   929                    {
       
   930                    addPathData(numSegments, pathSegments, pathData);
       
   931                    }        
       
   932                    addDrawPathCommand(path, paintMode);
       
   933            }, 
       
   934            {
       
   935                vgClearPath(mVgPath, VG_PATH_CAPABILITY_APPEND_TO);
       
   936                
       
   937                vgAppendPathData(mVgPath, numSegments, pathSegments, pathData);
       
   938                vgDrawPath(mVgPath, paintMode);
       
   939            });
       
   940     mDoStroke   = VG_FALSE;
       
   941     mDoFill     = VG_FALSE;
       
   942 }
       
   943 
       
   944 void HbNvgCsIcon::setTransform(HbDereferencer * iconData, quint32 & counter, const VGfloat* currentMatrix)
       
   945 {
       
   946     COND_COM_OC(mCreatingNvgIcon, ;, vgLoadMatrix(currentMatrix));
       
   947 
       
   948     quint32 lCommonData =  iconData->derefInt32();
       
   949     quint32 lTransformType = (lCommonData & 0x00ff0000) >> 16 ;
       
   950 
       
   951     VGfloat matrixTemp[9] = {
       
   952         1.0f, 0.0f, 0.0f,
       
   953         0.0f, 1.0f, 0.0f,
       
   954         0.0f, 0.0f, 1.0f
       
   955     };
       
   956 
       
   957     counter = 0;
       
   958 
       
   959     if (lTransformType != 1) {
       
   960         if (lTransformType == TRANSFORM_COMPLETE) {
       
   961             matrixTemp[0] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   962             matrixTemp[4] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   963             matrixTemp[3] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   964             matrixTemp[1] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   965             matrixTemp[6] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   966             matrixTemp[7] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   967         } else {
       
   968             if (lTransformType & TRANSFORM_ROTATION) {
       
   969                 //vgScale
       
   970                 matrixTemp[0] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   971                 matrixTemp[4] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   972                 
       
   973                 //vgShear
       
   974                 matrixTemp[3] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   975                 matrixTemp[1] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   976             } else {
       
   977                 if (lTransformType & TRANSFORM_SCALING) {
       
   978                     //vgScale
       
   979                     matrixTemp[0] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   980                     matrixTemp[4] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   981                 }
       
   982 
       
   983                 if (lTransformType & TRANSFORM_SHEARING) {
       
   984                     //vgShear
       
   985                     matrixTemp[3] = iconData->derefReal32((++counter) * sizeof (VGfloat));
       
   986                     matrixTemp[1] = iconData->derefReal32((++counter) * sizeof (VGfloat));;
       
   987                 }
       
   988             }
       
   989 
       
   990             if (lTransformType & TRANSFORM_TRANSLATION) {
       
   991                 //vgTranslate
       
   992                 matrixTemp[6] = iconData->derefReal32((++counter) * sizeof (VGfloat));;
       
   993                 matrixTemp[7] = iconData->derefReal32((++counter) * sizeof (VGfloat));;
       
   994             }
       
   995         }
       
   996 
       
   997         COND_COM_OC(mCreatingNvgIcon,
       
   998                     addSetTransformCommand(matrixTemp, 1),
       
   999                     vgMultMatrix(matrixTemp));
       
  1000     } else {
       
  1001         COND_COM_OC(mCreatingNvgIcon,
       
  1002                     addSetTransformCommand(matrixTemp, 0), ;);
       
  1003     }
       
  1004 }
       
  1005 
       
  1006 void HbNvgCsIcon::setStrokePaint(HbDereferencer * iconData)
       
  1007 {
       
  1008     COND_COM_OC_OOC(register int drawingMode = mCreatingNvgIcon;);
       
  1009     
       
  1010     quint32 lCommonData = iconData->derefInt32();
       
  1011     quint32 lStrokeType = lCommonData & 0x07;
       
  1012     quint16 lSpecifcData = (lCommonData >> 16) & 0xff;
       
  1013 
       
  1014     switch (lStrokeType) {
       
  1015     case STROKE_LGRAD: {
       
  1016         mGradPaintStroke = mPaintStroke;
       
  1017         
       
  1018         COND_COM_OC_OOC(
       
  1019                    if (mCreatingNvgIcon)
       
  1020                        {
       
  1021                        mGradPaintStroke = vgCreatePaint();
       
  1022                        if (mGradPaintStroke == VG_INVALID_HANDLE) {
       
  1023                            throw HbNvgException(HbNvgEngine::NvgErrBadHandle);
       
  1024                        }
       
  1025                        });
       
  1026               
       
  1027         // gradient data, the data will be word aligned
       
  1028         float* lGradData = (float*)iconData->derefInt8Array(4 * sizeof(VGfloat), sizeof(float));
       
  1029                    
       
  1030         COND_COM_OC(drawingMode, ; ,
       
  1031                     vgSetParameteri(mGradPaintStroke, VG_PAINT_TYPE, VG_PAINT_TYPE_LINEAR_GRADIENT);
       
  1032                     vgSetParameterfv(mGradPaintStroke, VG_PAINT_LINEAR_GRADIENT, 4, lGradData);
       
  1033                     vgSeti(VG_MATRIX_MODE, VG_MATRIX_STROKE_PAINT_TO_USER));
       
  1034 
       
  1035         if (lSpecifcData & 0x1) {
       
  1036             float* lGradMatrix1 = (float*)iconData->derefInt8Array(6 * sizeof(VGfloat),
       
  1037                     4 + 4 * sizeof(VGfloat));
       
  1038                             
       
  1039             float lGradMatrix[9] = {lGradMatrix1[0], lGradMatrix1[3], 0.0f,
       
  1040                                     lGradMatrix1[1], lGradMatrix1[4], 0.0f,
       
  1041                                     lGradMatrix1[2], lGradMatrix1[5], 1.0f
       
  1042                                    };
       
  1043 
       
  1044             COND_COM_OC(drawingMode,
       
  1045                         addStrokeLinearGradientCommand(4, lGradData, lGradMatrix, mGradPaintStroke),
       
  1046                         vgLoadMatrix(lGradMatrix));
       
  1047             Q_UNUSED(IdentityMatrix);
       
  1048         } else {
       
  1049             COND_COM_OC(drawingMode,
       
  1050                         addStrokeLinearGradientCommand(4, lGradData, (VGfloat*)IdentityMatrix, mGradPaintStroke),
       
  1051                         vgLoadIdentity());
       
  1052         }
       
  1053         vgSeti(VG_MATRIX_MODE, VG_MATRIX_PATH_USER_TO_SURFACE);
       
  1054     } 
       
  1055     break;
       
  1056     case STROKE_RGRAD: {
       
  1057         mGradPaintStroke = mPaintStroke;
       
  1058         
       
  1059         COND_COM_OC_OOC(
       
  1060                     if (mCreatingNvgIcon)
       
  1061                         {
       
  1062                         mGradPaintStroke = vgCreatePaint();
       
  1063                         if (mGradPaintStroke == VG_INVALID_HANDLE) {
       
  1064                             throw HbNvgException(HbNvgEngine::NvgErrBadHandle);
       
  1065                         }
       
  1066                         });
       
  1067         // gradient data, the data will be word aligned
       
  1068         float* lGradData = (float*)iconData->derefInt8Array(5 * sizeof(VGfloat), sizeof(quint32));
       
  1069 
       
  1070         COND_COM_OC(drawingMode, ; ,
       
  1071                     vgSetParameteri(mGradPaintStroke, VG_PAINT_TYPE, VG_PAINT_TYPE_RADIAL_GRADIENT);
       
  1072                     vgSetParameterfv(mGradPaintStroke, VG_PAINT_RADIAL_GRADIENT, 5, lGradData);
       
  1073                     vgSeti(VG_MATRIX_MODE, VG_MATRIX_STROKE_PAINT_TO_USER));
       
  1074 
       
  1075         if (lSpecifcData & 0x1) {
       
  1076             float* lGradMatrix1 = (float*)iconData->derefInt8Array(6 * sizeof(VGfloat),
       
  1077                 4 + 5 * sizeof(VGfloat));
       
  1078             float lGradMatrix[9] = {lGradMatrix1[0], lGradMatrix1[3], 0.0f,
       
  1079                                     lGradMatrix1[1], lGradMatrix1[4], 0.0f,
       
  1080                                     lGradMatrix1[2], lGradMatrix1[5], 1.0f
       
  1081                                    };
       
  1082 
       
  1083             COND_COM_OC(drawingMode,
       
  1084                         addStrokeRadialGradientCommand(4, lGradData, lGradMatrix, mGradPaintStroke),
       
  1085                         vgLoadMatrix(lGradMatrix));
       
  1086             Q_UNUSED(IdentityMatrix);
       
  1087         } else {
       
  1088             COND_COM_OC(drawingMode,
       
  1089                         addStrokeRadialGradientCommand(4, lGradData, (VGfloat*)IdentityMatrix, mGradPaintStroke),
       
  1090                         vgLoadIdentity());
       
  1091         }
       
  1092         vgSeti(VG_MATRIX_MODE, VG_MATRIX_PATH_USER_TO_SURFACE);
       
  1093         }
       
  1094         break;
       
  1095 
       
  1096     case STROKE_COLOR_RAMP: {
       
  1097         int lStopCount = lSpecifcData;
       
  1098         float* lStopData = (float*) iconData->derefInt8Array(lStopCount * 5 * sizeof(VGfloat), 4);
       
  1099 
       
  1100         if (mStrokeAlpha == 0xff) {
       
  1101             vgSetParameteri(mGradPaintStroke, VG_PAINT_COLOR_RAMP_SPREAD_MODE, VG_COLOR_RAMP_SPREAD_PAD);
       
  1102             vgSetParameterfv(mGradPaintStroke, VG_PAINT_COLOR_RAMP_STOPS, lStopCount*5, lStopData);
       
  1103         } else {
       
  1104             VGfloat *crs = new VGfloat[lStopCount * 5];
       
  1105             Q_CHECK_PTR(crs);
       
  1106             QScopedArrayPointer<VGfloat> colorRamps(crs);
       
  1107             // Copy color ramps and modify alpha
       
  1108             memcpy(colorRamps.data(), lStopData, lStopCount*5*sizeof(VGfloat));
       
  1109             VGfloat lAlphaInFloat = mStrokeAlpha * 0.003921568627450f; //(1.0f/255.0f);
       
  1110             VGfloat* lAlphaValue = &colorRamps[4];
       
  1111             for (int i = 0; i < lStopCount; i++) {
       
  1112                 *lAlphaValue *= lAlphaInFloat;
       
  1113                 lAlphaValue += 5;
       
  1114             }
       
  1115 
       
  1116             vgSetParameteri(mGradPaintStroke, VG_PAINT_COLOR_RAMP_SPREAD_MODE, VG_COLOR_RAMP_SPREAD_PAD);
       
  1117             vgSetParameterfv(mGradPaintStroke, VG_PAINT_COLOR_RAMP_STOPS, lStopCount*5, colorRamps.data());
       
  1118             }
       
  1119         }
       
  1120         break;
       
  1121 
       
  1122     default: {
       
  1123         quint32 lRgba = iconData->derefInt32(NVG_RGBA_OFS);
       
  1124         lRgba = (lRgba & 0xffffff00) | mStrokeAlpha; // replace alpha
       
  1125 
       
  1126         COND_COM_OC(drawingMode,
       
  1127                     addStrokeSetColorCommand(lRgba),
       
  1128                     vgSetParameteri(mPaintStroke, VG_PAINT_TYPE, VG_PAINT_TYPE_COLOR);
       
  1129                     vgSetColor(mPaintStroke, lRgba));
       
  1130         }
       
  1131         break;
       
  1132     }
       
  1133 }
       
  1134 
       
  1135 #ifdef    OPENVG_OBJECT_CACHING
       
  1136 VGPath HbNvgCsIcon::createPath()
       
  1137 {
       
  1138     VGPath path = VG_INVALID_HANDLE;
       
  1139     switch (mLastPathDataType) {
       
  1140     case NvgEightBitEncoding: {
       
  1141         path = vgCreatePath(VG_PATH_FORMAT_STANDARD,
       
  1142                             VG_PATH_DATATYPE_S_16, 1.0f / 2.0f, 0.0f, 0, 0,
       
  1143                             VG_PATH_CAPABILITY_APPEND_TO);
       
  1144     }
       
  1145     break;
       
  1146 
       
  1147     case NvgSixteenBitEncoding: {
       
  1148         path = vgCreatePath(VG_PATH_FORMAT_STANDARD,
       
  1149                             VG_PATH_DATATYPE_S_16, 1.0f / 16.0f, 0.0f, 0, 0,
       
  1150                             VG_PATH_CAPABILITY_APPEND_TO);
       
  1151     }
       
  1152     break;
       
  1153 
       
  1154     case NvgThirtyTwoBitEncoding: {
       
  1155         path = vgCreatePath(VG_PATH_FORMAT_STANDARD,
       
  1156                             VG_PATH_DATATYPE_S_32, 1.0f / 65536.0f, 0.0f, 0, 0,
       
  1157                             VG_PATH_CAPABILITY_APPEND_TO);
       
  1158     }
       
  1159     break;
       
  1160     default: {
       
  1161 
       
  1162     }
       
  1163     break;
       
  1164     }
       
  1165     return path;
       
  1166 }
       
  1167 #endif
       
  1168 
       
  1169 void HbNvgCsIcon::addPathData(VGint numSegments, const VGubyte * pathSegments, const void * pathData)
       
  1170 {
       
  1171     mNvgIconData->encodeInt32(NvgPathData);
       
  1172     mNvgIconData->encodeInt32(numSegments);
       
  1173     mNvgIconData->encodeData(pathSegments, numSegments);
       
  1174 
       
  1175     int coordinateCount = 0;
       
  1176     for (int i = 0; i < numSegments; ++i) {
       
  1177         switch (pathSegments[i]) {
       
  1178         case VG_HLINE_TO:
       
  1179         case VG_VLINE_TO:
       
  1180             coordinateCount += 1;
       
  1181             break;
       
  1182         case VG_MOVE_TO:
       
  1183         case VG_LINE_TO:
       
  1184         case VG_SQUAD_TO:
       
  1185             coordinateCount += 2;
       
  1186             break;
       
  1187         case VG_QUAD_TO:
       
  1188         case VG_SCUBIC_TO:
       
  1189             coordinateCount += 4;
       
  1190             break;
       
  1191         case VG_SCCWARC_TO:
       
  1192         case VG_SCWARC_TO:
       
  1193         case VG_LCCWARC_TO:
       
  1194         case VG_LCWARC_TO:
       
  1195             coordinateCount += 5;
       
  1196             break;
       
  1197         case VG_CUBIC_TO:
       
  1198             coordinateCount += 6;
       
  1199             break;
       
  1200         default:
       
  1201             break;
       
  1202         }
       
  1203     }
       
  1204     mNvgIconData->encodeInt16(coordinateCount);
       
  1205     mNvgIconData->encodeData(pathData, coordinateCount * 4);
       
  1206 }
       
  1207 
       
  1208 void HbNvgCsIcon::addDrawPathCommand(VGPath path, VGbitfield paintMode)
       
  1209 {
       
  1210     mOpenVgHandles->addPath(path);
       
  1211     mNvgIconData->encodeInt32(NvgPath);
       
  1212     mNvgIconData->encodeInt32(path);
       
  1213     mNvgIconData->encodeInt32(paintMode);
       
  1214 }
       
  1215 
       
  1216 void HbNvgCsIcon::addLinearGradientCommand(VGint count, VGfloat* gradientData, VGfloat* gradientMatrix, VGPaint paint)
       
  1217 {
       
  1218     mOpenVgHandles->addPaint(paint);
       
  1219     mNvgIconData->encodeInt32(NvgPaint);
       
  1220     addLinearGradientCommandData(paint, count, gradientData, gradientMatrix);
       
  1221 }
       
  1222 
       
  1223 void HbNvgCsIcon::addRadialGradientCommand(VGint count, VGfloat* gradientData, VGfloat* gradientMatrix, VGPaint paint)
       
  1224 {
       
  1225     mOpenVgHandles->addPaint(paint);
       
  1226     mNvgIconData->encodeInt32(NvgPaint);
       
  1227     addRadialGradientCommandData(paint, count, gradientData, gradientMatrix);
       
  1228 }
       
  1229 
       
  1230 void HbNvgCsIcon::addSetColorCommand(VGuint rgba)
       
  1231 {
       
  1232     mNvgIconData->encodeInt32(NvgPaint);
       
  1233     mNvgIconData->encodeInt32(VG_PAINT_TYPE_COLOR);
       
  1234     mNvgIconData->encodeInt32(rgba);
       
  1235 }
       
  1236 
       
  1237 void HbNvgCsIcon::addColorRampCommand(VGPaint paint)
       
  1238 {
       
  1239     mNvgIconData->encodeInt32(NvgColorRamp);
       
  1240     mNvgIconData->encodeInt32(paint);
       
  1241 }
       
  1242 
       
  1243 void HbNvgCsIcon::addSetTransformCommand(const VGfloat* transformMatrix, int aFlag)
       
  1244 {
       
  1245     mNvgIconData->encodeInt32(NvgTransform);
       
  1246     mNvgIconData->encodeData(transformMatrix, 9 * sizeof(VGfloat));
       
  1247     mNvgIconData->encodeInt32(aFlag);
       
  1248 }
       
  1249 
       
  1250 void HbNvgCsIcon::addSetStrokeWidthCommand(VGfloat strokeWidth)
       
  1251 {
       
  1252     mNvgIconData->encodeInt32(NvgStrokeWidth);
       
  1253     mNvgIconData->encodeReal32(strokeWidth);
       
  1254 }
       
  1255 
       
  1256 void HbNvgCsIcon::addSetStrokeMiterLimitCommand(VGfloat miterLimit)
       
  1257 {
       
  1258     mNvgIconData->encodeInt32(NvgStrokeMiterLimit);
       
  1259     mNvgIconData->encodeReal32(miterLimit);
       
  1260 }
       
  1261 
       
  1262 void HbNvgCsIcon::addStrokeLineJoinCapCommand(VGint capStyle, VGint joinStyle)
       
  1263 {
       
  1264     mNvgIconData->encodeInt32(NvgStrokeLineJoinCap);
       
  1265     mNvgIconData->encodeInt32(capStyle);
       
  1266     mNvgIconData->encodeInt32(joinStyle);
       
  1267 }
       
  1268 
       
  1269 void HbNvgCsIcon::addStrokeLinearGradientCommand(VGint count, VGfloat* gradientData, VGfloat* gradientMatrix, VGPaint paint)
       
  1270 {
       
  1271     mOpenVgHandles->addPaint(paint);
       
  1272     mNvgIconData->encodeInt32(NvgStrokePaint);
       
  1273     addLinearGradientCommandData(paint, count, gradientData, gradientMatrix);
       
  1274 }
       
  1275 
       
  1276 void HbNvgCsIcon::addStrokeRadialGradientCommand(VGint count, VGfloat* gradientData, VGfloat* gradientMatrix, VGPaint paint)
       
  1277 {
       
  1278     mOpenVgHandles->addPaint(paint);
       
  1279     mNvgIconData->encodeInt32(NvgStrokePaint);
       
  1280     addRadialGradientCommandData(paint, count, gradientData, gradientMatrix);
       
  1281 }
       
  1282 
       
  1283 void HbNvgCsIcon::addStrokeSetColorCommand(VGuint rgba)
       
  1284 {
       
  1285     mNvgIconData->encodeInt32(NvgStrokePaint);
       
  1286     addSetColorCommandData(rgba);
       
  1287 }
       
  1288 
       
  1289 void HbNvgCsIcon::addStrokeColorRampCommand(VGPaint paint)
       
  1290 {
       
  1291     mNvgIconData->encodeInt32(NvgStrokeColorRamp);
       
  1292     mNvgIconData->encodeInt32(paint);
       
  1293 }
       
  1294 
       
  1295 void HbNvgCsIcon::addLinearGradientCommandData(VGPaint paint, VGint count, VGfloat* gradientData, VGfloat* gradientMatrix)
       
  1296 {
       
  1297     mNvgIconData->encodeInt32(VG_PAINT_TYPE_LINEAR_GRADIENT);
       
  1298     mNvgIconData->encodeInt32(paint);
       
  1299     mNvgIconData->encodeInt32(count);
       
  1300     mNvgIconData->encodeData(gradientData, count * sizeof(VGfloat));
       
  1301     mNvgIconData->encodeData(gradientMatrix, 9 * sizeof(VGfloat));
       
  1302 }
       
  1303 
       
  1304 void HbNvgCsIcon::addRadialGradientCommandData(VGPaint paint, VGint count, VGfloat* gradientData, VGfloat* gradientMatrix)
       
  1305 {
       
  1306     mNvgIconData->encodeInt32(VG_PAINT_TYPE_RADIAL_GRADIENT);
       
  1307     mNvgIconData->encodeInt32(paint);
       
  1308     mNvgIconData->encodeInt32(count);
       
  1309     mNvgIconData->encodeData(gradientData, count * sizeof(VGfloat));
       
  1310     mNvgIconData->encodeData(gradientMatrix, 9 * sizeof(VGfloat));
       
  1311 }
       
  1312 
       
  1313 void HbNvgCsIcon::addSetColorCommandData(VGuint rgba)
       
  1314 {
       
  1315     mNvgIconData->encodeInt32(VG_PAINT_TYPE_COLOR);
       
  1316     mNvgIconData->encodeInt32(rgba);
       
  1317 }
       
  1318 
       
  1319 HbNvgEngine::NvgErrorType HbNvgCsIcon::draw(const QSize &size)
       
  1320 {
       
  1321     NVG_DEBUGP2("DRAWING NVGCSIcon %s, ", __FUNCTION__);
       
  1322 
       
  1323     HbNvgEngine::NvgErrorType error = HbNvgEngine::NvgErrNone;
       
  1324 
       
  1325     // Get Matrix modes and all caller matrices (must be restored afterwards)
       
  1326     updateClientMatrices();
       
  1327 
       
  1328     //Exception handling has to happen
       
  1329     error =  doDraw(size);
       
  1330 
       
  1331     // restore everything as we may have changed matrix mode
       
  1332     restoreClientMatrices();
       
  1333 
       
  1334     return error;
       
  1335 }
       
  1336 
       
  1337 HbNvgEngine::NvgErrorType HbNvgCsIcon::doDraw(const QSize &size)
       
  1338 {
       
  1339     HbNvgEngine::NvgErrorType ret = HbNvgEngine::NvgErrNone;
       
  1340 
       
  1341     vgSetPaint(mPaintFill,   VG_FILL_PATH);
       
  1342     vgSetPaint(mPaintStroke, VG_STROKE_PATH);
       
  1343     mLastFillPaintColor     = 0;
       
  1344     mLastStrkePaintColor    = 0;
       
  1345     mLastFillPaintType      = 0;
       
  1346     mLastStrokePaintType    = 0;
       
  1347 
       
  1348     VGfloat lCurrentPathMatrix[9];
       
  1349     vgGetMatrix(lCurrentPathMatrix);
       
  1350 
       
  1351     vgSeti(VG_MATRIX_MODE, VG_MATRIX_PATH_USER_TO_SURFACE);
       
  1352     vgLoadMatrix(lCurrentPathMatrix);
       
  1353     setRotation();
       
  1354 #ifdef __MIRROR_  
       
  1355     vgScale(1.0f, -1.0f);
       
  1356     vgTranslate(0, (VGfloat)(-size.height()));
       
  1357 #endif
       
  1358 
       
  1359     setViewBoxToViewTransformation(size);
       
  1360 
       
  1361     vgSeti(VG_MATRIX_MODE, VG_MATRIX_PATH_USER_TO_SURFACE);
       
  1362 
       
  1363     VGfloat currentMatrix[9];
       
  1364 
       
  1365     vgGetMatrix(currentMatrix);
       
  1366     
       
  1367     mNvgIconData->beginRead();
       
  1368 
       
  1369     while (!mNvgIconData->eof()) {
       
  1370         switch (mNvgIconData->readInt32()) {
       
  1371         case NvgPath: {
       
  1372             VGPath path = (VGPath)mNvgIconData->readInt32();
       
  1373             VGPaintMode paintMode = (VGPaintMode)mNvgIconData->readInt32();
       
  1374 
       
  1375             if (path == VG_INVALID_HANDLE) {
       
  1376                 vgDrawPath(mVgPath, paintMode);
       
  1377             } else {
       
  1378                 vgDrawPath(path, paintMode);
       
  1379             }
       
  1380             break;
       
  1381         }
       
  1382         case NvgPathData: {
       
  1383             if (mVgPath != VG_INVALID_HANDLE) {
       
  1384             
       
  1385                 VGint numSegments = mNvgIconData->readInt32();
       
  1386                 
       
  1387                 VGubyte *pSegArry = new VGubyte[numSegments];
       
  1388                 Q_CHECK_PTR(pSegArry);
       
  1389                 QScopedArrayPointer<VGubyte> pathSegments(pSegArry);
       
  1390                 mNvgIconData->read(pathSegments.data(), numSegments);
       
  1391                 
       
  1392                 VGint coordinateCount = mNvgIconData->readInt32();
       
  1393                 
       
  1394                 VGubyte *pDataArry = new VGubyte[coordinateCount * 4];
       
  1395                 Q_CHECK_PTR(pDataArry);
       
  1396                 QScopedArrayPointer<VGubyte> pathData(pDataArry);
       
  1397                 mNvgIconData->read(pathData.data(), coordinateCount * 4);
       
  1398                 
       
  1399                 vgClearPath(mVgPath, VG_PATH_CAPABILITY_APPEND_TO);
       
  1400                 vgAppendPathData(mVgPath, numSegments, pathSegments.data(), pathData.data());
       
  1401             }
       
  1402             break;
       
  1403             }
       
  1404         case NvgPaint: {
       
  1405             drawPaint(mPaintFill, VG_MATRIX_FILL_PAINT_TO_USER, mLastFillPaintType, mLastFillPaintColor, VG_FILL_PATH);
       
  1406             break;
       
  1407             }
       
  1408         case NvgColorRamp: {
       
  1409             mNvgIconData->readInt32();
       
  1410             break;
       
  1411             }
       
  1412         case NvgTransform: {
       
  1413             int flag;
       
  1414             VGfloat transformMatrix[9];
       
  1415 
       
  1416             mNvgIconData->read((quint8 *)transformMatrix, 9 * sizeof(VGfloat));
       
  1417             flag = mNvgIconData->readInt32();
       
  1418 
       
  1419             vgLoadMatrix(currentMatrix);
       
  1420             if (flag) {
       
  1421                 vgMultMatrix(transformMatrix);
       
  1422             }
       
  1423             
       
  1424             break;
       
  1425             }
       
  1426         case NvgStrokeWidth: {
       
  1427             VGfloat strokeWidth = mNvgIconData->readReal32();
       
  1428             vgSetf(VG_STROKE_LINE_WIDTH, strokeWidth);
       
  1429             break;
       
  1430             }
       
  1431         
       
  1432         case NvgStrokeMiterLimit: {
       
  1433             VGfloat miterLimit = mNvgIconData->readReal32();
       
  1434             vgSetf(VG_STROKE_MITER_LIMIT, miterLimit);
       
  1435             break;
       
  1436             }
       
  1437         
       
  1438         case NvgStrokeLineJoinCap: {
       
  1439             VGint lineJoin = mNvgIconData->readInt32();
       
  1440             VGint cap = mNvgIconData->readInt32();
       
  1441 
       
  1442             vgSeti(VG_STROKE_JOIN_STYLE, (VGJoinStyle)lineJoin);
       
  1443             vgSeti(VG_STROKE_CAP_STYLE, (VGCapStyle)cap);
       
  1444             break;
       
  1445             }
       
  1446         case NvgStrokePaint: {
       
  1447             drawPaint(mPaintStroke, VG_MATRIX_STROKE_PAINT_TO_USER, mLastStrokePaintType, mLastStrkePaintColor, VG_STROKE_PATH);
       
  1448             break;
       
  1449             }
       
  1450         case NvgStrokeColorRamp: {
       
  1451             mNvgIconData->readInt32();
       
  1452             break;
       
  1453             }
       
  1454         default: {  
       
  1455             throw HbNvgException(HbNvgEngine::NvgErrCorrupt);
       
  1456             }
       
  1457         }
       
  1458     }
       
  1459 
       
  1460     mNvgIconData->endRead();
       
  1461 
       
  1462     return ret;
       
  1463 }
       
  1464 
       
  1465 void HbNvgCsIcon::drawColorRamp(VGPaint paint)
       
  1466 {
       
  1467     int stopCount = mNvgIconData->readInt32();
       
  1468     
       
  1469     VGfloat *crs = new VGfloat[stopCount];
       
  1470     Q_CHECK_PTR(crs);
       
  1471     QScopedArrayPointer<VGfloat> colorRamps(crs);
       
  1472 
       
  1473     mNvgIconData->read((quint8 *)colorRamps.data(), stopCount * sizeof(VGfloat));
       
  1474     vgSetParameteri(paint, VG_PAINT_COLOR_RAMP_SPREAD_MODE, VG_COLOR_RAMP_SPREAD_PAD);
       
  1475     vgSetParameterfv(paint, VG_PAINT_COLOR_RAMP_STOPS, stopCount, colorRamps.data());
       
  1476 }
       
  1477 
       
  1478 void HbNvgCsIcon::drawPaint(VGPaint paint, VGMatrixMode matrixMode, quint32 & lastPaintType, quint32 &lastPaintColor, VGPaintMode paintMode)
       
  1479 {
       
  1480     VGPaintType paintType = (VGPaintType)mNvgIconData->readInt32();
       
  1481 
       
  1482     if (paintType == VG_PAINT_TYPE_LINEAR_GRADIENT ||
       
  1483             paintType == VG_PAINT_TYPE_RADIAL_GRADIENT) {
       
  1484         VGPaintParamType paintPType = VG_PAINT_LINEAR_GRADIENT;
       
  1485         if (paintType == VG_PAINT_TYPE_RADIAL_GRADIENT) {
       
  1486             paintPType = VG_PAINT_RADIAL_GRADIENT;
       
  1487         }
       
  1488 
       
  1489         VGPaint paintHandle = mNvgIconData->readInt32();
       
  1490         int count = mNvgIconData->readInt32();
       
  1491         VGfloat gradientData[5];
       
  1492         VGfloat gradientMatrix[9];
       
  1493 
       
  1494         mNvgIconData->read((quint8 *)gradientData, count * sizeof(VGfloat));
       
  1495         mNvgIconData->read((quint8 *)gradientMatrix, 9 * sizeof(VGfloat));
       
  1496 
       
  1497         if (paintHandle) {
       
  1498             vgSetPaint(paintHandle,   paintMode);
       
  1499             vgSeti(VG_MATRIX_MODE, matrixMode);
       
  1500             vgLoadMatrix(gradientMatrix);
       
  1501             if (paintMode == VG_FILL_PATH) {
       
  1502                 mResetFillPaint = 1;
       
  1503             } else {
       
  1504                 mResetStrokePaint = 1;
       
  1505             }
       
  1506         } else {
       
  1507             if (lastPaintType != (quint32)paintType) {
       
  1508                 vgSetParameteri(paint, VG_PAINT_TYPE, paintType);
       
  1509             }
       
  1510             vgSetParameterfv(paint, paintPType, count, gradientData);
       
  1511 
       
  1512             vgSeti(VG_MATRIX_MODE, matrixMode);
       
  1513             vgLoadMatrix(gradientMatrix);
       
  1514         }
       
  1515         vgSeti(VG_MATRIX_MODE, VG_MATRIX_PATH_USER_TO_SURFACE);
       
  1516     } else if (paintType == VG_PAINT_TYPE_COLOR) {
       
  1517         if (paintMode == VG_FILL_PATH && mResetFillPaint) {
       
  1518             mResetFillPaint = 0;
       
  1519             vgSetPaint(paint, paintMode);
       
  1520         } else if (paintMode == VG_STROKE_PATH && mResetStrokePaint) {
       
  1521             mResetStrokePaint = 0;
       
  1522             vgSetPaint(paint, paintMode);
       
  1523         }
       
  1524         quint32 color = static_cast<quint32>(mNvgIconData->readInt32());
       
  1525         if (lastPaintType != (quint32)paintType) {
       
  1526             vgSetParameteri(paint, VG_PAINT_TYPE, VG_PAINT_TYPE_COLOR);
       
  1527             vgSetColor(paint, color);
       
  1528         } else {
       
  1529             if (lastPaintColor != color) {
       
  1530                 vgSetColor(paint, color);
       
  1531             }
       
  1532         }
       
  1533         lastPaintColor = color;
       
  1534     } else {
       
  1535         throw HbNvgException(HbNvgEngine::NvgErrCorrupt);
       
  1536     }
       
  1537     lastPaintType = paintType;
       
  1538 }
       
  1539 
       
  1540 void HbNvgCsIcon::setViewBoxToViewTransformation(const QSize &size)
       
  1541 {
       
  1542     HbNvgFitToViewBoxImpl *viewBoxTx = new HbNvgFitToViewBoxImpl();
       
  1543     Q_CHECK_PTR(viewBoxTx);
       
  1544     QScopedPointer<HbNvgFitToViewBoxImpl> fitToViewBoxImpl(viewBoxTx);
       
  1545 
       
  1546     fitToViewBoxImpl->setAlign(mPreserveAspectSetting);
       
  1547     fitToViewBoxImpl->setScaling(mSmilFitSetting);
       
  1548     fitToViewBoxImpl->setViewBox(mViewBoxX, mViewBoxY, mViewBoxW, mViewBoxH);
       
  1549     fitToViewBoxImpl->setWindowViewportTrans(QRect(0, 0, size.width(), size.height()), QSize(0, 0));
       
  1550 }
       
  1551 
       
  1552 void HbNvgCsIcon::setRotation()
       
  1553 {
       
  1554     if (mRotationAngle) {    
       
  1555         vgTranslate(mRotationX, mRotationY);             
       
  1556         vgRotate(mRotationAngle);
       
  1557         vgTranslate(-mRotationX, -mRotationY);
       
  1558     }
       
  1559 }
       
  1560 
       
  1561 void HbNvgCsIcon::updateClientMatrices()
       
  1562 {
       
  1563     mMatrixMode = vgGeti(VG_MATRIX_MODE);
       
  1564     vgSeti(VG_MATRIX_MODE, VG_MATRIX_PATH_USER_TO_SURFACE);
       
  1565     vgGetMatrix(mPathMatrix);
       
  1566     vgSeti(VG_MATRIX_MODE, VG_MATRIX_IMAGE_USER_TO_SURFACE);
       
  1567     vgGetMatrix(mImageMatrix);
       
  1568     vgSeti(VG_MATRIX_MODE, mMatrixMode);
       
  1569 }
       
  1570 
       
  1571 void HbNvgCsIcon::restoreClientMatrices()
       
  1572 {
       
  1573     vgSeti(VG_MATRIX_MODE, VG_MATRIX_PATH_USER_TO_SURFACE);
       
  1574     vgLoadMatrix(mPathMatrix);
       
  1575     vgSeti(VG_MATRIX_MODE, VG_MATRIX_IMAGE_USER_TO_SURFACE);
       
  1576     vgLoadMatrix(mImageMatrix);
       
  1577     vgSeti(VG_MATRIX_MODE, mMatrixMode);
       
  1578 }
       
  1579 
       
  1580 QPoint HbNvgCsIcon::getTranslatedPoint(VGfloat *trMatrix, const QPoint &point)
       
  1581 {
       
  1582     QPoint trPoint;
       
  1583 
       
  1584     trPoint.setX(trMatrix[0] * point.x() + trMatrix[3] * point.y() + trMatrix[6]);
       
  1585     trPoint.setY(trMatrix[1] * point.x() + trMatrix[4] * point.y() + trMatrix[7]);
       
  1586 
       
  1587     return trPoint;
       
  1588 }
       
  1589 
       
  1590 VGfloat HbNvgCsIcon::minVal4(VGfloat x1, VGfloat x2, VGfloat x3, VGfloat x4)
       
  1591 {
       
  1592     VGfloat min = x1;
       
  1593 
       
  1594     if (min > x2) {
       
  1595         min = x2;
       
  1596     }
       
  1597     if (min > x3) {
       
  1598         min = x3;
       
  1599     }
       
  1600     if (min > x4) {
       
  1601         min = x4;
       
  1602     }
       
  1603 
       
  1604     return min;
       
  1605 }
       
  1606 
       
  1607 VGfloat HbNvgCsIcon::maxVal4(VGfloat x1, VGfloat x2, VGfloat x3, VGfloat x4)
       
  1608 {
       
  1609     VGfloat max = x1;
       
  1610 
       
  1611     if (max < x2) {
       
  1612         max = x2;
       
  1613     }
       
  1614     if (max < x3) {
       
  1615         max = x3;
       
  1616     }
       
  1617     if (max < x4) {
       
  1618         max = x4;
       
  1619     }
       
  1620 
       
  1621     return max;
       
  1622 }
       
  1623