2012-08-22 67 views
2

在我的iPad繪圖應用程序中,我創建了一個768 x 1024的緩衝區上下文,並用它來加速我的繪圖。iPad繪圖:將圖像繪製到CGContext中

這是我目前正在執行時的drawRect被調用,簡單地複製了我現有的繪製到屏幕上的代碼:從我的背景情況下它收集和圖片:

CGContextRef context = UIGraphicsGetCurrentContext(); 

CGImageRef image = CGBitmapContextCreateImage([DrawingState sharedState].context); 
CGContextDrawImage(context, CGRectMake(0, 0, 768, 1024), image); 
CGImageRelease(image); 

此代碼的工作就如同預期並將其繪製到我當前的上下文中,然後釋放圖像。有用!

不過,我做了一些性能優化,以加快我的畫,我想這個代碼,而不是,這裏的「矩形」是的drawRect傳入的矩形

CGContextRef context = UIGraphicsGetCurrentContext(); 

CGImageRef image = CGBitmapContextCreateImage([DrawingState sharedState].context); 
CGImageRef subImage = CGImageCreateWithImageInRect(image, rect); 
CGContextDrawImage(context, rect, subImage); 
CGImageRelease(subImage); 
CGImageRelease(image); 

這不起作用,圖像不會出現在正確的位置,甚至可能不是正確的圖像(不能說,因爲如果圖像出現在錯誤的位置,圖像的一部分將不會繪製,因爲它將在drawRect的外部矩形。)任何想法是怎麼回事?

下面是我如何初始化[DrawingState sharedState] .context。這部分應該沒問題,但我想我會把它包括在內以求完整。

if(context != NULL) 
{ 
    CGContextRelease(context); 
    context = NULL; 
} 
if(bitmapData != NULL) 
{ 
    free(bitmapData); 
    bitmapData = NULL; 
} 
if(colorSpace != NULL) 
{ 
    CGColorSpaceRelease(colorSpace); 
    colorSpace = NULL; 
} 

CGSize canvasSize = CGSizeMake(screenWidth, screenHeight); 

int bitmapByteCount; 
int bitmapBytesPerRow; 

bitmapBytesPerRow = (canvasSize.width * 4); 
bitmapByteCount  = (bitmapBytesPerRow * canvasSize.height); 

colorSpace = CGColorSpaceCreateDeviceRGB(); 

bitmapData = malloc(bitmapByteCount); 

if(bitmapData == NULL){ 
    NSLog(@"Buffer could not be alloc'd"); 
} 

//Create the context 
context = CGBitmapContextCreate(bitmapData, canvasSize.width, canvasSize.height, 8, bitmapBytesPerRow, colorSpace, kCGImageAlphaPremultipliedFirst); 

根據要求,我嘗試執行的實際優化如下。我正在繪製緩衝區圖像(在執行其他繪圖之前)到我的緩衝區上下文中,然後將我的緩衝區上下文複製到當前上下文中。

原始代碼:

CGContextClearRect([DrawingState sharedState].context, CGRectMake(0, 0, 768, 1024)); 
if(bufferImage != NULL) 
{ 
    CGContextDrawImage([DrawingState sharedState].context, CGRectMake(0, 0, 768, 1024), bufferImage); 
} 

優化代碼:

CGContextClearRect([DrawingState sharedState].context, rect); 
if(bufferImage != NULL) 
{ 
    CGImageRef subImage = CGImageCreateWithImageInRect(bufferImage, rect); 
    CGContextDrawImage([DrawingState sharedState].context, rect, bufferImage); 
    CGImageRelease(subImage); 
} 

回答

0

這個問題的答案的簡短版本是,我想使用CGContextClipToRect而不是嘗試獲取子圖像。 CGContextClipToRect(CGContextRef,CGRect)用於自動將任何圖形剪輯到提供的矩形外的上下文中。

0

我懷疑你要使用相同的rect值創建一個子圖像和繪畫。

如果您閱讀the docsCGImageCreateWithImageInRect取圖像和rect參數的交集,而CGContextDrawImage將繪製圖像到rect中。

我不明白你打算如何使用這個作爲優化,但你的結果聽起來像我期望從你的代碼。

+0

請您詳細說明一下好嗎? 「圖像」是一個完整尺寸的圖像。 subImage是(應該是)屏幕需要刷新的部分。然後,根據需要刷新的矩形,將subImage「粘貼」到currentContext中。在這種情況下,你認爲哪種「錯誤」?此外,這不是我正在嘗試做的確切優化,但我注意到它與我嘗試的優化具有完全相同的問題,並且更容易顯示其他人。 – MikeS

+0

drawRect:的rect參數取自本地視圖座標空間,但您的緩衝區位於屏幕座標空間中。所以你正在從錯誤的緩衝區「切割」。我建議看一下UIView文檔「在視圖座標系之間轉換」。在那裏你可以找到幫助你的功能。具體來說,您要將使用的矩形與CGImageCreateWithImageInRect一起轉換爲屏幕(窗口)座標。 –

+0

我目前的觀點是屏幕的大小,所以我不認爲這應該是一個問題,對嗎?我已經做了一些正在通過的矩形日誌記錄,矩形看起來像我期望通過。 – MikeS