diff --git a/AppKit/CoreGraphics/CGColor.j b/AppKit/CoreGraphics/CGColor.j index 9f141c80c..7b8ee6088 100644 --- a/AppKit/CoreGraphics/CGColor.j +++ b/AppKit/CoreGraphics/CGColor.j @@ -150,19 +150,21 @@ function CGColorCreateGenericCMYK(cyan, magenta, yellow, black, alpha) */ function CGColorCreateCopyWithAlpha(aColor, anAlpha) { - var components = aColor.components; + if ( !aColor ) return aColor; // Avoid error null pointer in next line - if (!aColor || anAlpha == components[components.length - 1]) + var components = aColor.components.slice(); + + if (anAlpha == components[components.length - 1]) return aColor; + // set new alpha value now so that a potentially a new cache entry is made and + // not that an existing cache entry is mutated. + components[components.length - 1] = anAlpha; + if (aColor.pattern) - var copy = CGColorCreateWithPattern(aColor.colorspace, aColor.pattern, components); + return CGColorCreateWithPattern(aColor.colorspace, aColor.pattern, components); else - var copy = CGColorCreate(aColor.colorspace, components); - - copy.components[components.length - 1] = anAlpha; - - return copy; + return CGColorCreate(aColor.colorspace, components); } /*! diff --git a/Tests/AppKit/CGColorTest.j b/Tests/AppKit/CGColorTest.j index bb4bf2be6..f437b1d46 100644 --- a/Tests/AppKit/CGColorTest.j +++ b/Tests/AppKit/CGColorTest.j @@ -2,6 +2,33 @@ @implementation CGColorTest : OJTestCase +- (void)testColorCreateReturnNullIfNull +{ + [self assert:NULL equals:CGColorCreate( NULL, [1,2,3] ) message:"colorspace null failed"]; + [self assert:NULL + equals:CGColorCreate( CGColorSpaceCreateDeviceRGB(), NULL ) + message:"components null failed"]; +} + +- (void)testColorCreateEnsureComponentsAreCopied +{ + var colorspace = CGColorSpaceCreateDeviceRGB(), + components = [2,3,4,5], + clr = CGColorCreate(colorspace, components); + + components[0] = components[1] = components[2] = components[3] = 0; + [self assert:[1,1,1,1] equals:clr.components]; + [self assert:[0,0,0,0] equals:components]; +} + +- (void)testColorCreateCachesColorsAlphaChangeIsPropagated +{ + var clr = CGColorCreate(CGColorSpaceCreateDeviceRGB(), [0.4, 0.3, 0.2, 0.2]), + newclr = CGColorCreate(CGColorSpaceCreateDeviceRGB(), [0.4, 0.3, 0.2, 0.2]); + newclr.components[newclr.components.length - 1] = 0.6; + [self assert:0.6 equals:clr.components[clr.components.length-1]]; +} + - (void)testColorCreate { var colorspace = CGColorSpaceCreateDeviceRGB(), @@ -63,5 +90,119 @@ [self assert:NULL equals:clr.pattern message:"pattern failed"]; } +- (void)testColorCreateWithPattern +{ + var clrspc = CGColorSpaceCreateDeviceRGB(), + pattern = "a new pattern", + components = [0.2, 0.4, 0.6, 0.8], + clr = CGColorCreateWithPattern(clrspc, pattern, components); + + [self assert:clrspc equals:clr.colorspace]; + [self assert:pattern equals:clr.pattern]; + [self assert:components equals:clr.components]; + + // ensure that there was a copy made of the components + components[0] = components[1] = components[2] = components[3] = 0.0; + [self assert:[0.2, 0.4, 0.6, 0.8] equals:clr.components]; + + // ensure that null is returned + [self assert:NULL equals:CGColorCreateWithPattern(NULL, "a new pattern", [])]; + [self assert:NULL equals:CGColorCreateWithPattern(CGColorSpaceCreateDeviceRGB(), + NULL, [])]; + [self assert:NULL equals:CGColorCreateWithPattern(CGColorSpaceCreateDeviceRGB(), + "a new pattern", NULL)]; + [self assert:NULL equals:CGColorCreateWithPattern(NULL, NULL, NULL)]; +} + +- (void)testColorGetAlpha +{ + var clr = CGColorCreateGenericCMYK(0.2, 0.3, 0.4, 0.5, 0.6); + [self assert:0.6 equals:CGColorGetAlpha(clr)]; +} + +- (void)testColorGetColorSpace +{ + var clr = CGColorCreateGenericCMYK(0.2, 0.3, 0.4, 0.5, 0.6); + [self assert:CGColorSpaceCreateDeviceCMYK() + equals:CGColorGetColorSpace(clr)]; +} + +- (void)testColorGetComponents +{ + var clr = CGColorCreateGenericCMYK(0.2, 0.3, 0.4, 0.5, 0.6); + [self assert:[ROUND(0.2*255)/255, ROUND(0.3*255)/255, ROUND(0.4*255)/255, + ROUND(0.5*255)/255, ROUND(0.6*255)/255] + equals:CGColorGetComponents(clr)]; +} + +- (void)testColorGetNumberOfComponents +{ + var clr = CGColorCreateGenericCMYK(0.2, 0.3, 0.4, 0.5, 0.6); + [self assert:5 equals:CGColorGetNumberOfComponents(clr)]; +} + +- (void)testColorGetPattern +{ + var clr = CGColorCreateWithPattern(CGColorSpaceCreateDeviceRGB(), "a new pattern", + [1,1,1,1]); + [self assert:"a new pattern" equals:CGColorGetPattern(clr)]; +} + +- (void)testColorCreateCopyWithAlphaWithPattern +{ + var clr = CGColorCreateWithPattern(CGColorSpaceCreateDeviceRGB(), "a new pattern", + [1,1,1,1]); + [self assert:1 equals:CGColorGetAlpha(clr) message:"initial alpha"]; + + var newclr = CGColorCreateCopyWithAlpha(clr, 0.6); + [self assert:0.6 equals:CGColorGetAlpha(newclr) message:"new color alpha value"]; + [self assert:1 equals:CGColorGetAlpha(clr) message:"alpha after copy"]; + + [self assert:clr.colorspace equals:newclr.colorspace message:"newclr colorspace failed"]; + [self assert:clr.pattern equals:newclr.pattern message:"newclr pattern failed"]; +} + +- (void)testColorCreateCopyWithAlphaWithComponents +{ + var clr = CGColorCreateGenericRGB(0.4, 0.3, 0.2, 0.3); + [self assert:0.3 equals:CGColorGetAlpha(clr) message:"initial alpha"]; + + var newclr = CGColorCreateCopyWithAlpha(clr, 0.6); + [self assert:0.6 equals:CGColorGetAlpha(newclr) message:"new color alpha value"]; + [self assert:0.3 equals:CGColorGetAlpha(clr) message:"alpha after copy"]; + + [self assert:CGColorSpaceCreateDeviceRGB() + equals:newclr.colorspace message:"newclr colorspace failed"]; + [self assert:[ROUND(0.4*255)/255,ROUND(0.3*255)/255,ROUND(0.2*255)/255,0.6] + equals:newclr.components message:"newclr components failed"]; + [self assert:NULL equals:newclr.pattern message:"newclr pattern failed"]; + + [self assert:CGColorSpaceCreateDeviceRGB() + equals:clr.colorspace message:"orig clr colorspace failed"]; + [self assert:[ROUND(0.4*255)/255,ROUND(0.3*255)/255,ROUND(0.2*255)/255,0.3] + equals:clr.components message:"orig clr components failed"]; + [self assert:NULL equals:clr.pattern message:"orig clr pattern failed"]; +} + +- (void)testColorCreateCopyWithAlphaWithComponentsNullColor +{ + [self assert:NULL + equals:CGColorCreateCopyWithAlpha(NULL,0.5) + message:"null color failed"]; + + var clr = CGColorCreateGenericRGB(0.4,0.3,0.2,0.1), + newclr = CGColorCreateCopyWithAlpha(clr, 0.1); + [self assert:clr equals:newclr]; +} + +- (void)testColorEqualToColor +{ + var clr1 = CGColorCreateGenericRGB(0.4, 0.3, 0.2, 0.3); + [self assert:true equals:CGColorEqualToColor(NULL,NULL)]; + [self assert:false equals:CGColorEqualToColor(NULL,clr1)]; + [self assert:true equals:CGColorEqualToColor(clr1,clr1)]; + [self assert:false equals:CGColorEqualToColor(clr1,NULL)]; +} + @end