kjhari02 Posted March 3, 2010 Share Posted March 3, 2010 I need some help in drawing an ellipse with fill and border, both having different alpha color The code is, <?php $img = imageCreateTrueColor( 600, 600); $red = imagecolorallocatealpha($img, 255, 0, 0,50); $blue = imagecolorallocatealpha($img, 0, 0, 255,50); imagefilledellipse ($img, 300, 300, 400, 400, $red); imagefilledellipse ($img, 300, 300, 350, 350, $blue); header( 'Content-Type: image/png' ); imagePNG( $img ); imagedestroy($img); ?> The image that I'm expecting is the test.png that I've attached with this post. But the output that I'm getting now is result.png (as attached) Can anyone please help me with this. Regards, Hari [attachment deleted by admin] Quote Link to comment Share on other sites More sharing options...
aeroswat Posted March 3, 2010 Share Posted March 3, 2010 I need some help in drawing an ellipse with fill and border, both having different alpha color The code is, <?php $img = imageCreateTrueColor( 600, 600); $red = imagecolorallocatealpha($img, 255, 0, 0,50); $blue = imagecolorallocatealpha($img, 0, 0, 255,50); imagefilledellipse ($img, 300, 300, 400, 400, $red); imagefilledellipse ($img, 300, 300, 350, 350, $blue); header( 'Content-Type: image/png' ); imagePNG( $img ); imagedestroy($img); ?> The image that I'm expecting is the test.png that I've attached with this post. But the output that I'm getting now is result.png (as attached) Can anyone please help me with this. Regards, Hari What package is this? And can this produce pie charts and graphs and stuff? Quote Link to comment Share on other sites More sharing options...
teamatomic Posted March 3, 2010 Share Posted March 3, 2010 You are going to have to play with your colors, not all blues are pure blue. And if you are going to really compare colors and expect exact representation to the eye you have to calibrate your monitor. For what you want try adding a bit of red and green to blue, 80,80,240 maybe. HTH Teamatomic Quote Link to comment Share on other sites More sharing options...
Psycho Posted March 3, 2010 Share Posted March 3, 2010 The function takes parameters for separate RGB values. So, this $blue = imagecolorallocatealpha($img, 0, 0, 255,50); Red = 0, Green = 0, Blue = 255, could be expected to be the same as the HTML equivalent of #0000ff, which is close to the color in the test image. But, that function also takes a fourth parameter (the alpha channel) for opacity! You are laying the blue image on top of the red image and the opacity is set at 50, which is somewhat transparent. So, some of the red from the first circle is bleeding through the blue. Since I am assuming you want the blue to have the slightly subdued appearance as opposed to being completely opaque, my suggestioin would be that after you create the red circle and before you create the blue circle, you should create a completely opaque white circle (alpha set to 0) at the same size and position as you will be placing the blue circle. The blue circle will then be placed on top of a white background. If you get a funny looking edge around the blue circle try decreasing the size of the white circle slightly. Quote Link to comment Share on other sites More sharing options...
Psycho Posted March 3, 2010 Share Posted March 3, 2010 I just tested it and the blue came out perfectly (although my image defaulted to a black background which messes up the red. I suspect you are setting the initial background to white?). This code gives me the EXACT image you showed you were after above: <?php $img = imageCreateTrueColor( 600, 600); $red = imagecolorallocatealpha($img, 255, 0, 0, 50); $white = imagecolorallocatealpha($img, 255, 255, 255, 0); $blue = imagecolorallocatealpha($img, 0, 0, 255, 50); imagefill ($img, 0, 0, $white); imagefilledellipse ($img, 300, 300, 400, 400, $red); imagefilledellipse ($img, 300, 300, 350, 350, $white); imagefilledellipse ($img, 300, 300, 350, 350, $blue); header( 'Content-Type: image/png' ); imagePNG( $img );imagedestroy($img); ?> Quote Link to comment Share on other sites More sharing options...
kjhari02 Posted March 3, 2010 Author Share Posted March 3, 2010 Hi mjdamato, Thanks for the help. This worked... well sort of. I actually want the blue color to have an alpha too so that other shapes drawn below it can be visible. This is actually part of a much bigger project and this is the only thing which is missing. The ellipse can be drawn on top of other shapes/images and so if the blue color has an alpha then the background must also be visible. Any thoughts?? Quote Link to comment Share on other sites More sharing options...
kjhari02 Posted March 3, 2010 Author Share Posted March 3, 2010 This is the code how I'm visualisizing the other shapes at the background. <?php $img = imageCreateTrueColor( 600, 600); $red = imagecolorallocatealpha($img, 255, 0, 0, 50); $white = imagecolorallocatealpha($img, 255, 255, 255, 0); $blue = imagecolorallocatealpha($img, 0, 0, 255, 50); $green = imagecolorallocate($img, 0, 255, 0); imagefill ($img, 0, 0, $white); //Draw the background shape..a rectangle imagefilledrectangle($img, 0,0,300,300, $green); //Now draw the ellipse imagefilledellipse ($img, 300, 300, 400, 400, $red); imagefilledellipse ($img, 300, 300, 350, 350, $white); imagefilledellipse ($img, 300, 300, 350, 350, $blue); header( 'Content-Type: image/png' ); imagePNG( $img );imagedestroy($img); ?> Quote Link to comment Share on other sites More sharing options...
Psycho Posted March 3, 2010 Share Posted March 3, 2010 Well, your original code was doing what it was supposed to do then - the red image was showing through the blue image. Although, I think I understand, what you are trying to accomplish. The only solution I can see is to do as one poster suggested above and modify the blue color (with the red showing through) to achieve the color you want. EDIT: After a little trial and error I think you can get close to what you want by changing the Alpha value for the $white color. Try setting it to 50 and see what you think. EDIT #2: Or you could look into using imagefilledarc() to create the red outer circle around the blue circle so it isn't underneath the blue circle. Quote Link to comment Share on other sites More sharing options...
teamatomic Posted March 3, 2010 Share Posted March 3, 2010 Put this under your color allocations, have not tried it with alpha, YMMV. imagecolortransparent($img, $red); HTH Teamatomic Quote Link to comment Share on other sites More sharing options...
kjhari02 Posted March 3, 2010 Author Share Posted March 3, 2010 Hi mjdamato, I tried the imagefillearc to draw the outline image but the output was very very very bad.. Maybe I'm going wrong somewhere. Here's the script imagesetthickness($img, 20); imagefilledarc ( $img , $centerx, $centery, $w, $h , 0, 360 , $red , IMG_ARC_NOFILL ); and the output is [attachment deleted by admin] Quote Link to comment Share on other sites More sharing options...
kjhari02 Posted March 3, 2010 Author Share Posted March 3, 2010 Hi teamatomic, That didn't work out.. I also thought that imagecolortransparent would set that particular color in the image to transparent and tried to set the imagecolortransparent($img,$white); in hopes that the white color that I drew second time (as per mjdamato's suggestion) would turn transparent. Didn't work either. Quote Link to comment Share on other sites More sharing options...
Psycho Posted March 3, 2010 Share Posted March 3, 2010 Hmm, I tried using imagecolortransparent() but with no positive results. BUt, I think I found a solution. When creating the blue circle we want it to have the set color with bleed-through for the green square but not the red circle. So, using the same code as above, I created a completely opaque white circle so the blue circle would have the right color. But, since you want to have the green from the square show through - I created a 90 degree green arc on the white circle before placing the blue circle. <?php $img = imageCreateTrueColor( 600, 600); $white = imagecolorallocatealpha($img, 255, 255, 255, 0); $green = imagecolorallocate($img, 0, 255, 0); $red = imagecolorallocatealpha($img, 255, 0, 0, 50); $blue = imagecolorallocatealpha($img, 0, 0, 255, 50); imagefill ($img, 0, 0, $white); //Draw the background shape..a rectangle imagefilledrectangle($img, 0,0,300,300, $green); //Now draw the objects imagefilledellipse ($img, 300, 300, 400, 400, $red); imagefilledellipse ($img, 300, 300, 350, 350, $white); imagefilledarc($img, 300, 300, 350, 350, 180, 270, $green, IMG_ARC_PIE); imagefilledellipse ($img, 300, 300, 350, 350, $blue); header( 'Content-Type: image/png' ); imagePNG( $img );imagedestroy($img); ?> Quote Link to comment Share on other sites More sharing options...
teamatomic Posted March 3, 2010 Share Posted March 3, 2010 Yea, I wasnt sure if transparent would work with an alpha allocation. If you would want to go the transparent route probably would have to just allocate a straight color then use transparent on it. HTH Teamatomic Quote Link to comment Share on other sites More sharing options...
kjhari02 Posted March 3, 2010 Author Share Posted March 3, 2010 Hi mjdamato, Thanks for the code. It works splendidly but the code assumes that the square will always be there. But my issue is that there could be any element anywhere (heck it could also be another ellipse at the back placed anywhere). For e.g <?php $img = imageCreateTrueColor( 600, 600); $white = imagecolorallocatealpha($img, 255, 255, 255, 0); $green = imagecolorallocate($img, 0, 255, 0); $red = imagecolorallocatealpha($img, 255, 0, 0, 50); $blue = imagecolorallocatealpha($img, 0, 0, 255, 50); imagefill ($img, 0, 0, $white); //Draw the background shape..a rectangle imagefilledrectangle($img, 20,100,500,500, $green); //Now draw the objects imagefilledellipse ($img, 300, 300, 400, 400, $red); imagefilledellipse ($img, 300, 300, 350, 350, $white); imagefilledarc($img, 300, 300, 350, 350, 180, 270, $green, IMG_ARC_PIE); imagefilledellipse ($img, 300, 300, 350, 350, $blue); header( 'Content-Type: image/png' ); imagePNG( $img );imagedestroy($img); ?> This time the image is not proper. or is there a way of drawing an antialiased unfilled ellipse with a stroke and alpha color? This might also help me. Regards, Hari Quote Link to comment Share on other sites More sharing options...
Psycho Posted March 4, 2010 Share Posted March 4, 2010 I'm out of ideas then. I had already tried creating a solid color on top of the red circle and then setting it to transparent before placing the blue circle. That didn't work for me - it appears the transparency only applies to the specific color after the image is complete. I also tried using imagesetthickness() and imageellipse() to just create a red outer ring. Looking at the descriptions and examples in the manual it shoudl work, but the output was always just a 1 pixel wide ring. Seems to be a bug as the manual states: imagesetthickness() sets the thickness of the lines drawn when drawing rectangles, polygons, ellipses etc. etc. to thickness pixels The only other option I can think of would be to create the red/blue circle as above (with a solid white circle in the middle) as a separate object and then merging that object on top of whatever other elements you need. Not really sure and don't intend to invest the time. Good luck to you. Quote Link to comment Share on other sites More sharing options...
kjhari02 Posted March 4, 2010 Author Share Posted March 4, 2010 No problem mydamato. Thanks for the help still Let me know if you come across anything like this. Quote Link to comment Share on other sites More sharing options...
kjhari02 Posted March 8, 2010 Author Share Posted March 8, 2010 I finally figured out how to do it and thought I might share with you too... public function drawCircle($w,$h,$stroke,$scolor,$salpha,$fcolor){ $multiplier = 2; $w=$w*$multiplier; $h=$h*$multiplier; $aw = (($w>$h)?($w)$h)); $stroke*=$multiplier*2; $img = imageCreateTrueColor( $w,$h ); imagealphablending($img,true); imageantialias($img, true); imagesavealpha($img, true); $color = imageColorAllocateAlpha( $img, 255, 255, 255, 127); imagefill( $img, 5, 5, $color ); //Create the border imageellipse($img, ($w)/2, ($h)/2, $w, $h ,$scolor ); imageellipse($img, ($w)/2, ($h)/2, $w-$stroke, $h-$stroke ,$scolor ); imagefilltoborder($img, (($w)/2)-($w/2)+($stroke/4), (($h)/2), $scolor, $scolor); //Create the transparency for the border $trans = imageCreateTrueColor( $w,$h ); imagealphablending($trans,true); imageantialias($trans, true); imagesavealpha($trans, true); $color = ImageColorAllocateAlpha( $trans, 255, 255, 255, 127); imagefill( $trans, 5, 5, $color ); imagecopymerge_alpha($trans , $img , 0, 0, 0, 0, $w, $h , $salpha); imagedestroy($img); $img = $trans; //Draw the fill color //$blue = imagecolorallocatealpha($img, 0, 0, 255,100); imagefilledellipse ($img,($w)/2, ($h)/2,$w-$stroke, $h-$stroke,$fcolor); $resizedimage = imagecreatetruecolor(($w)/$multiplier, $h/$multiplier); imagealphablending($resizedimage,true); imageantialias($resizedimage, true); imagesavealpha($resizedimage, true); $color = imageColorAllocateAlpha( $resizedimage, 255, 255, 255, 127); imagefill( $resizedimage, 5, 5, $color ); imagecopyresampled($resizedimage , $img, 0, 0, 0, 0, ($w)/$multiplier, ($h)/$multiplier, ($w), ($h)); imagedestroy($img); return $resizedimage; } Hope this helps someone Quote Link to comment Share on other sites More sharing options...
kjhari02 Posted March 10, 2010 Author Share Posted March 10, 2010 Forgot to post the other method used ... private function imagecopymerge_alpha($dst_im, $src_im, $dst_x, $dst_y, $src_x, $src_y, $src_w, $src_h, $pct){ if(!isset($pct)){ return false; } //$pct /= 100; // Get image width and height $w = imagesx( $src_im ); $h = imagesy( $src_im ); // Turn alpha blending off imagealphablending( $src_im, false ); // Find the most opaque pixel in the image (the one with the smallest alpha value) $minalpha = 127; for( $x = 0; $x < $w; $x++ ) for( $y = 0; $y < $h; $y++ ){ $alpha = ( imagecolorat( $src_im, $x, $y ) >> 24 ) & 0xFF; if( $alpha < $minalpha ){ $minalpha = $alpha; } } //loop through image pixels and modify alpha for each for( $x = 0; $x < $w; $x++ ){ for( $y = 0; $y < $h; $y++ ){ //get current alpha value (represents the TANSPARENCY!) $colorxy = imagecolorat( $src_im, $x, $y ); $alpha = ( $colorxy >> 24 ) & 0xFF; //calculate new alpha if( $minalpha !== 127 ){ $alpha = 127 + 127 * $pct * ( $alpha - 127 ) / ( 127 - $minalpha ); } else { $alpha += 127 * $pct; } //get the color index with new alpha $alphacolorxy = imagecolorallocatealpha( $src_im, ( $colorxy >> 16 ) & 0xFF, ( $colorxy >> 8 ) & 0xFF, $colorxy & 0xFF, $alpha ); //set pixel with the new color + opacity if( !imagesetpixel( $src_im, $x, $y, $alphacolorxy ) ){ return false; } } } // The image copy imagecopy($dst_im, $src_im, $dst_x, $dst_y, $src_x, $src_y, $src_w, $src_h); } Quote Link to comment Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.