//----------------------------------------------------------------------------- void CGDrawContext::applyLineStyle (CGContextRef context) { switch (currentState.lineStyle.getLineCap ()) { case CLineStyle::kLineCapButt: CGContextSetLineCap (context, kCGLineCapButt); break; case CLineStyle::kLineCapRound: CGContextSetLineCap (context, kCGLineCapRound); break; case CLineStyle::kLineCapSquare: CGContextSetLineCap (context, kCGLineCapSquare); break; } switch (currentState.lineStyle.getLineJoin ()) { case CLineStyle::kLineJoinMiter: CGContextSetLineJoin (context, kCGLineJoinMiter); break; case CLineStyle::kLineJoinRound: CGContextSetLineJoin (context, kCGLineJoinRound); break; case CLineStyle::kLineJoinBevel: CGContextSetLineJoin (context, kCGLineJoinBevel); break; } if (currentState.lineStyle.getDashCount () > 0) { CGFloat* dashLengths = new CGFloat [currentState.lineStyle.getDashCount ()]; for (int32_t i = 0; i < currentState.lineStyle.getDashCount (); i++) { dashLengths[i] = currentState.frameWidth * currentState.lineStyle.getDashLengths ()[i]; } CGContextSetLineDash (context, currentState.lineStyle.getDashPhase (), dashLengths, currentState.lineStyle.getDashCount ()); delete [] dashLengths; } }
void GraphicsContext::setLineJoin(LineJoin join) { if (paintingDisabled()) return; switch (join) { case MiterJoin: CGContextSetLineJoin(platformContext(), kCGLineJoinMiter); break; case RoundJoin: CGContextSetLineJoin(platformContext(), kCGLineJoinRound); break; case BevelJoin: CGContextSetLineJoin(platformContext(), kCGLineJoinBevel); break; } }
bool GiCanvasIos::beginPaintBuffered(bool fast, bool autoscale) { if (m_draw->getContext() || !gs() || !m_draw->createBufferBitmap(m_draw->width(), m_draw->height(), autoscale ? m_draw->_scale : 1.f)) { return false; } RECT_2D clipBox = { 0, 0, m_draw->width(), m_draw->height() }; owner()->_beginPaint(clipBox); m_draw->_fast = fast; m_draw->_ctxused[0] = false; m_draw->_ctxused[1] = false; CGContextRef context = m_draw->getContext(); bool antiAlias = !fast && gs()->isAntiAliasMode(); CGContextSetAllowsAntialiasing(context, antiAlias); CGContextSetShouldAntialias(context, antiAlias); CGContextSetFlatness(context, fast ? 20 : 1); CGContextSetLineCap(context, kCGLineCapRound); CGContextSetLineJoin(context, kCGLineJoinRound); owner()->setMaxPenWidth(-1, 0.5f / m_draw->_scale); return true; }
bool GiCanvasIos::beginPaint(CGContextRef context, bool fast, bool buffered) { if (m_draw->getContext() || !context) return false; if (gs()) { CGRect rc = CGContextGetClipBoundingBox(context); RECT_2D clipBox = { rc.origin.x, rc.origin.y, rc.origin.x + rc.size.width, rc.origin.y + rc.size.height }; owner()->_beginPaint(clipBox); } m_draw->_context = context; m_draw->_fast = fast; m_draw->_ctxused[0] = false; m_draw->_ctxused[1] = false; if (buffered && gs()) { m_draw->createBufferBitmap(m_draw->width(), m_draw->height(), m_draw->_scale); context = m_draw->getContext(); } bool antiAlias = !fast && (!gs() || gs()->isAntiAliasMode()); CGContextSetAllowsAntialiasing(context, antiAlias); CGContextSetShouldAntialias(context, antiAlias); CGContextSetFlatness(context, fast ? 20 : 1); CGContextSetLineCap(context, kCGLineCapRound); CGContextSetLineJoin(context, kCGLineJoinRound); if (owner()) // 设置最小线宽为0.5像素,使用屏幕放大倍数以便得到实际像素值 owner()->setMaxPenWidth(-1, 0.5f / m_draw->_scale); return true; }
static void quartzPrepareLine (GraphicsScreen me) { CGContextSetLineJoin (my d_macGraphicsContext, kCGLineJoinRound); if (my duringXor) { CGContextSetBlendMode (my d_macGraphicsContext, kCGBlendModeDifference); CGContextSetAllowsAntialiasing (my d_macGraphicsContext, false); CGContextSetRGBStrokeColor (my d_macGraphicsContext, 1.0, 1.0, 1.0, 1.0); } else { CGContextSetRGBStrokeColor (my d_macGraphicsContext, my d_macColour.red / 65536.0, my d_macColour.green / 65536.0, my d_macColour.blue / 65536.0, 1.0); } double lineWidth_pixels = LINE_WIDTH_IN_PIXELS (me); CGContextSetLineWidth (my d_macGraphicsContext, lineWidth_pixels); CGFloat lengths [4]; if (my lineType == Graphics_DOTTED) lengths [0] = my resolution > 192 ? my resolution / 100.0 : 2, lengths [1] = my resolution > 192 ? my resolution / 75.0 + lineWidth_pixels : 2; if (my lineType == Graphics_DASHED) lengths [0] = my resolution > 192 ? my resolution / 25 : 6, lengths [1] = my resolution > 192 ? my resolution / 50.0 + lineWidth_pixels : 2; if (my lineType == Graphics_DASHED_DOTTED) lengths [0] = my resolution > 192 ? my resolution / 25 : 6, lengths [1] = my resolution > 192 ? my resolution / 50.0 + lineWidth_pixels : 2; lengths [2] = my resolution > 192 ? my resolution / 100.0 : 2; lengths [3] = my resolution > 192 ? my resolution / 50.0 + lineWidth_pixels : 2; CGContextSetLineDash (my d_macGraphicsContext, 0.0, my lineType == Graphics_DRAWN ? NULL : lengths, my lineType == 0 ? 0 : my lineType == Graphics_DASHED_DOTTED ? 4 : 2); }
static void Quartz_SetLineJoin(R_GE_linejoin ljoin, NewDevDesc *dd) { QuartzDesc *xd = (QuartzDesc*)dd->deviceSpecific; CGLineJoin linejoin; switch (ljoin) { case GE_ROUND_JOIN: linejoin = kCGLineJoinRound; break; case GE_MITRE_JOIN: linejoin = kCGLineJoinMiter; break; case GE_BEVEL_JOIN: linejoin = kCGLineJoinBevel; break; default: error(_("Invalid line join")); } CGContextSetLineJoin( GetContext(xd), linejoin); }
static void quartzgen_begin_page(GVJ_t *job) { CGRect bounds = CGRectMake(0.0, 0.0, job->width, job->height); if (!job->context) { switch (job->device.id) { case FORMAT_PDF: { /* create the auxiliary info for PDF content, author and title */ CFStringRef auxiliaryKeys[] = { kCGPDFContextCreator, kCGPDFContextTitle }; CFStringRef auxiliaryValues[] = { CFStringCreateWithFormat(kCFAllocatorDefault, NULL, CFSTR("%s %s"), job->common->info[0], job->common->info[1]), job->obj->type == ROOTGRAPH_OBJTYPE ? CFStringCreateWithBytesNoCopy(kCFAllocatorDefault, (const UInt8 *)job->obj->u.g->name, strlen(job->obj->u.g->name), kCFStringEncodingUTF8, false, kCFAllocatorNull) : CFSTR("") }; CFDictionaryRef auxiliaryInfo = CFDictionaryCreate( kCFAllocatorDefault, (const void **)&auxiliaryKeys, (const void **)&auxiliaryValues, sizeof(auxiliaryValues)/sizeof(auxiliaryValues[0]), &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks ); /* create a PDF for drawing into */ CGDataConsumerRef data_consumer = CGDataConsumerCreate(job, &device_data_consumer_callbacks); job->context = CGPDFContextCreate(data_consumer, &bounds, auxiliaryInfo); /* clean up */ CGDataConsumerRelease(data_consumer); CFRelease(auxiliaryInfo); int i; for (i = 0; i < sizeof(auxiliaryValues)/sizeof(auxiliaryValues[0]); ++i) CFRelease(auxiliaryValues[i]); } break; default: /* bitmap formats */ { size_t bytes_per_row = (job->width * BYTES_PER_PIXEL + BYTE_ALIGN) & ~BYTE_ALIGN; void* buffer = NULL; #if __ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__ >= 20000 /* iPhoneOS has no swap files for memory, so if we're short of memory we need to make our own temp scratch file to back it */ size_t buffer_size = job->height * bytes_per_row; mach_msg_type_number_t vm_info_size = HOST_VM_INFO_COUNT; vm_statistics_data_t vm_info; if (host_statistics(mach_host_self(), HOST_VM_INFO, (host_info_t)&vm_info, &vm_info_size) != KERN_SUCCESS || buffer_size * 2 > vm_info.free_count * vm_page_size) { FILE* temp_file = tmpfile(); if (temp_file) { int temp_file_descriptor = fileno(temp_file); if (temp_file_descriptor >= 0 && ftruncate(temp_file_descriptor, buffer_size) == 0) { buffer = mmap( NULL, buffer_size, PROT_READ | PROT_WRITE, MAP_FILE | MAP_SHARED, temp_file_descriptor, 0); if (buffer == (void*)-1) buffer = NULL; } fclose(temp_file); } } if (!buffer) buffer = mmap( NULL, buffer_size, PROT_READ | PROT_WRITE, MAP_ANON| MAP_SHARED, -1, 0); #endif /* create a true color bitmap for drawing into */ CGColorSpaceRef color_space = CGColorSpaceCreateDeviceRGB(); job->context = CGBitmapContextCreate( buffer, /* data: MacOSX lets system allocate, iPhoneOS use manual memory mapping */ job->width, /* width in pixels */ job->height, /* height in pixels */ BITS_PER_COMPONENT, /* bits per component */ bytes_per_row, /* bytes per row: align to 16 byte boundary */ color_space, /* color space: device RGB */ kCGImageAlphaPremultipliedFirst /* bitmap info: premul ARGB has best support in OS X */ ); job->imagedata = CGBitmapContextGetData((CGContextRef)job->context); /* clean up */ CGColorSpaceRelease(color_space); } break; } } /* start the page (if this is a paged context) and graphics state */ CGContextRef context = (CGContextRef)job->context; CGContextBeginPage(context, &bounds); CGContextSaveGState(context); CGContextSetMiterLimit(context, 1.0); CGContextSetLineJoin(context, kCGLineJoinRound); /* set up the context transformation */ CGContextScaleCTM(context, job->scale.x, job->scale.y); CGContextRotateCTM(context, -job->rotation * M_PI / 180.0); CGContextTranslateCTM(context, job->translation.x, job->translation.y); }
static void MusicBoxDrawIndicator(HIViewRef view, CGContextRef mboxctx) { if (!showIndicator) return; // Bar const double length[] = { 1.0, 1.0 }; CGContextSetLineWidth(mboxctx, mbxBarWidth); CGContextSetLineDash(mboxctx, 0, length, 2); CGContextSetLineJoin(mboxctx, kCGLineJoinMiter); CGContextBeginPath(mboxctx); double x = mbxOffsetX + mbxMarginX + mbxBarWidth / 2.0; for (int h = 0; h < 8; h++) { // Inactive CGContextSetRGBStrokeColor(mboxctx, (196.0 / 256.0), (200.0 / 256.0), (176.0 / 256.0), 1.0); CGContextMoveToPoint (mboxctx, x, mbxOffsetY + mbxMarginY); CGContextAddLineToPoint(mboxctx, x, mbxOffsetY + mbxMarginY + mbxBarHeight); CGContextMoveToPoint (mboxctx, x + mbxRightBarX, mbxOffsetY + mbxMarginY); CGContextAddLineToPoint(mboxctx, x + mbxRightBarX, mbxOffsetY + mbxMarginY + mbxBarHeight); CGContextStrokePath(mboxctx); // Max Channel *ch = &SoundData.channels[h]; ch->envx = ch->xenvx >> 4; ch-> left_vol_level = (ch->xenvx * ch->volume_left ) >> 11; ch->right_vol_level = (ch->xenvx * ch->volume_right) >> 11; short vl = ch-> left_vol_level; short vr = ch->right_vol_level; long long currentTime; if (vl <= 0) vl = 0; else if (vl > 64) vl = 64; else vl = (short) (yyscale * sqrt((double) vl)) & (~0 << 1); if (vr <= 0) vr = 0; else if (vr > 64) vr = 64; else vr = (short) (yyscale * sqrt((double) vr)) & (~0 << 1); if (vl < prevLVol[h]) vl = ((prevLVol[h] + vl) >> 1); if (vr < prevRVol[h]) vr = ((prevRVol[h] + vr) >> 1); Microseconds((UnsignedWide *) ¤tTime); // left if ((vl >= prevLMax[h]) && (vl > prevLVol[h])) { barTimeL[h] = currentTime; prevLMax[h] = vl; } else if ((prevLMax[h] > 0) && (barTimeL[h] + 1000000 > currentTime)) { CGContextSetRGBStrokeColor(mboxctx, (22.0 / 256.0), (156.0 / 256.0), (20.0 / 256.0), (double) (barTimeL[h] + 1000000 - currentTime) / 1000000.0); CGContextMoveToPoint (mboxctx, x, mbxOffsetY + mbxMarginY + (double) (prevLMax[h] - 2)); CGContextAddLineToPoint(mboxctx, x, mbxOffsetY + mbxMarginY + (double) (prevLMax[h] )); CGContextStrokePath(mboxctx); } else prevLMax[h] = 0; prevLVol[h] = vl; // right if ((vr >= prevRMax[h]) && (vr > prevRVol[h])) { barTimeR[h] = currentTime; prevRMax[h] = vr; } else if ((prevRMax[h] > 0) && (barTimeR[h] + 1000000 > currentTime)) { CGContextSetRGBStrokeColor(mboxctx, (22.0 / 256.0), (156.0 / 256.0), (20.0 / 256.0), (double) (barTimeR[h] + 1000000 - currentTime) / 1000000.0); CGContextMoveToPoint (mboxctx, x + mbxRightBarX, mbxOffsetY + mbxMarginY + (double) (prevRMax[h] - 2)); CGContextAddLineToPoint(mboxctx, x + mbxRightBarX, mbxOffsetY + mbxMarginY + (double) (prevRMax[h] )); CGContextStrokePath(mboxctx); } else prevRMax[h] = 0; prevRVol[h] = vr; // Active CGContextSetRGBStrokeColor(mboxctx, (22.0 / 256.0), (22.0 / 256.0), (20.0 / 256.0), 1.0); CGContextMoveToPoint (mboxctx, x, mbxOffsetY + mbxMarginY); CGContextAddLineToPoint(mboxctx, x, mbxOffsetY + mbxMarginY + (double) vl); CGContextStrokePath(mboxctx); CGContextMoveToPoint (mboxctx, x + mbxRightBarX, mbxOffsetY + mbxMarginY); CGContextAddLineToPoint(mboxctx, x + mbxRightBarX, mbxOffsetY + mbxMarginY + (double) vr); CGContextStrokePath(mboxctx); x += (mbxBarWidth + mbxBarSpace); } }
void CFX_QuartzDeviceDriver::setStrokeInfo(const CFX_GraphStateData* graphState, FX_ARGB argb, FX_FLOAT lineWidth) { if (NULL == graphState) { return; } CGContextSetLineWidth(_context, lineWidth); CGLineCap cap; switch (graphState->m_LineCap) { case CFX_GraphStateData::LineCapRound: { cap = kCGLineCapRound; break; } case CFX_GraphStateData::LineCapSquare: { cap = kCGLineCapSquare; break; } case CFX_GraphStateData::LineCapButt: default: { cap = kCGLineCapButt; } } CGContextSetLineCap(_context, cap); CGLineJoin join; switch (graphState->m_LineJoin) { case CFX_GraphStateData::LineJoinRound: { join = kCGLineJoinRound; break; } case CFX_GraphStateData::LineJoinBevel: { join = kCGLineJoinBevel; break; } case CFX_GraphStateData::LineJoinMiter: default: { join = kCGLineJoinMiter; } } CGContextSetLineJoin(_context, join); if (graphState->m_DashCount) { #if CGFLOAT_IS_DOUBLE CGFloat* dashArray = new CGFloat[graphState->m_DashCount]; if (!dashArray) { return; } for (int index = 0; index < graphState->m_DashCount; ++index) { dashArray[index] = graphState->m_DashArray[index]; } #else CGFloat* dashArray = (CGFloat*)graphState->m_DashArray; #endif CGContextSetLineDash(_context, graphState->m_DashPhase, dashArray, graphState->m_DashCount); #if CGFLOAT_IS_DOUBLE delete[] dashArray; #endif } FX_INT32 a, r, g, b; ArgbDecode(argb, a, r, g, b); CGContextSetRGBStrokeColor(_context, r / 255.f, g / 255.f, b / 255.f, a / 255.f); }
void CGContextSetLineJoin_wrap(CGContext *con, int j) { CGContextSetLineJoin(con, CGLineJoin(j)); }
void MyTimerProc ( EventLoopTimerRef inTimer, void *inUserData ) { WindowRef window = (WindowRef)inUserData; static int i = 0; static int j = 0; static int step = 5; GrafPtr curPort; CGContextRef context; CGrafPtr windowPort = GetWindowPort( window ); GetPort(&curPort); SetPort(windowPort); CreateCGContextForPort( windowPort, &context ); // Do our drawing in here CGContextSetGrayFillColor( context, 0.0, 1.0 ); CGContextFillRect( context, CGRectMake( 0, 0, 800, 600 ) ); CGContextSetGrayFillColor( context, 1.0, 1.0 ); CGContextSetRGBStrokeColor( context, 1.0, 0.0, 0.0, 1.0 ); CGContextSetLineWidth( context, 5.0 ); CGContextSetLineCap( context, kCGLineCapRound ); CGContextSetLineJoin( context, kCGLineJoinRound ); CGContextSetMiterLimit( context, 5 ); // Draw each of the 4 transform demos // // 1. Translate - move the origin, draw the graphic // Place the origin in the llh corner of the upper left quadrant CGContextSaveGState( context ); CGContextTranslateCTM( context, i / 2, i / 2 + 300 ); CGContextRotateCTM( context, -2.0 * 3.1416 / 8 ); drawGraphic( context, 0, 0 ); CGContextRestoreGState( context ); // 2. Rotate - move origin, do rotation, draw the graphic // Put the origin back into the llh corner of the upper right quadrant CGContextSaveGState( context ); if ( j < 1000/2 ) { // Rotate around left circle CGContextTranslateCTM( context, 500, 450 ); CGContextRotateCTM( context, -j * 3.1416 * 2.0 / 500.0 - 3.1416 ); CGContextTranslateCTM( context, -100, -20 ); drawGraphic( context, 0, 0 ); } if ( j >= 1000/2 ) { // Rotate under bottom half and over top right 1/4 CGContextTranslateCTM( context, 700, 450 ); CGContextRotateCTM( context, j * 3.1416 * 2.0 / 500.0 ); CGContextScaleCTM( context, 1, 1 ); CGContextTranslateCTM( context, -100, 20 ); CGContextRotateCTM( context, 3.1416 ); drawGraphic( context, 0, 0 ); } CGContextRestoreGState( context ); // 3. Scale - move origin, set scale, draw the graphic CGContextSaveGState( context ); CGContextScaleCTM( context, i * 400.0 / 500.0 / 40.0, i * 300.0 / 500.0 / 40.0 ); CGContextRotateCTM( context, -3.1416 / 4 ); drawGraphic( context, 0, 0 ); CGContextRestoreGState( context ); // 4. Show the basic graphic CGContextTranslateCTM( context, 600, 150 ); drawGraphic( context, 0, 0 ); CGContextFlush( context ); CGContextRelease( context ); SetPort ( curPort ); i += step; j += abs( step ); if ( i >= 500 ) { step = -step; } if ( i <= 0 ) { step = -step; j = 0; } }