1

カスタム UITableViewCell 背景に使用している角が丸いグラデーションがあります。パスにストロークを適用しようとしていますが、まったく実行できず、どこが間違っているのかわかりません。

  CGFloat minx = CGRectGetMinX(rect) , midx = CGRectGetMidX(rect), maxx = CGRectGetMaxX(rect) ;
  CGFloat miny = CGRectGetMinY(rect) , maxy = CGRectGetMaxY(rect) ;
  minx = minx + 1;
  miny = miny ;

  maxx = maxx - 1;
  maxy = maxy - 1;

  CGContextMoveToPoint(c, minx, miny);
  CGContextAddArcToPoint(c, minx, maxy, midx, maxy, kDefaultMargin);
  CGContextAddArcToPoint(c, maxx, maxy, maxx, miny, kDefaultMargin);
  CGContextAddLineToPoint(c, maxx, miny);
  CGContextAddLineToPoint(c, minx, miny);

  // Fill and stroke the path
  CGContextClip(c);
  CGContextStrokePath(c);  

  CGFloat locations[2] = { 0.0, 1.0 };
  CGFloat mycomponents[8] = TABLE_CELL_BACKGROUND;
  CGColorSpaceRef myColorspace = CGColorSpaceCreateDeviceRGB();
  CGGradientRef myGradient = CGGradientCreateWithColorComponents(myColorspace, mycomponents, locations, 2);
  CGContextDrawLinearGradient(c, myGradient, CGPointMake(minx,miny), CGPointMake(minx,maxy), 0);
  CGGradientRelease(myGradient);
  CGColorSpaceRelease(myColorspace);

このコードは、四角形を右に丸め、グラデーションを適用しますが、行をストロークしません。私の間違いはどこですか?

代替テキスト http://grab.by/26Ye



編集: subw の推奨に従って、コードを次のように変更しました。

    CGContextRef c = UIGraphicsGetCurrentContext();
    CGColorSpaceRef myColorspace = CGColorSpaceCreateDeviceRGB();
    CGGradientRef myGradient = nil;
    CGFloat components[8] = TABLE_CELL_BACKGROUND;
    CGContextSetFillColorWithColor(c, [[UIColor redColor] CGColor]);
    CGContextSetStrokeColorWithColor(c, [[UAColor redColor] CGColor]);
    CGContextSetLineWidth(c, 2);

    CGFloat minx = CGRectGetMinX(rect) , midx = CGRectGetMidX(rect), maxx = CGRectGetMaxX(rect) ;
    CGFloat miny = CGRectGetMinY(rect) , maxy = CGRectGetMaxY(rect) ;
    minx = minx + 1;
    miny = miny ;

    maxx = maxx - 1;
    maxy = maxy - 1;

    CGContextMoveToPoint(c, minx, miny);
    CGContextAddArcToPoint(c, minx, maxy, midx, maxy, kDefaultMargin);
    CGContextAddArcToPoint(c, maxx, maxy, maxx, miny, kDefaultMargin);
    CGContextAddLineToPoint(c, maxx, miny);
    CGContextAddLineToPoint(c, minx, miny);

    // Fill and stroke the path
    CGContextSaveGState(c);
    CGContextClip(c);

    CGFloat locations[2] = { 0.0, 1.0 };
    CGFloat mycomponents[8] = TABLE_CELL_BACKGROUND;
    CGColorSpaceRef myColorspace = CGColorSpaceCreateDeviceRGB();
    myGradient = CGGradientCreateWithColorComponents(myColorspace, mycomponents, locations, 2);
    CGContextDrawLinearGradient(c, myGradient, CGPointMake(minx,miny), CGPointMake(minx,maxy), 0);

    CGContextRestoreGState(c);
    CGContextStrokePath(c);

でも直角はこんな感じで…</p>

代替テキスト http://grab.by/2714

...国境なし。を に変更するCGContextStrokePath(c)CGContextStrokeRect(c, rect)、ストロークが表示されます (わかりやすくするために赤にしました)。しかし、どういうわけか、パスをストロークするとき、ストロークがありません:(

代替テキスト http://grab.by/27aM

4

3 に答える 3

5

改訂されたコードに対応して、ドキュメントを引用します。

現在のパスとは異なり、現在のクリッピング パスはグラフィックス状態の一部です。したがって、クリッピング パスを以前の状態に復元してペイント可能領域を再び拡大するには、クリップする前にグラフィックス状態を保存し、クリップされた描画が完了した後にグラフィックス状態を復元する必要があります。

新しいクリッピング パスを決定した後、関数はコンテキストの現在のパスを空のパスにリセットします。

—<a href="http://developer.apple.com/iphone/library/documentation/GraphicsImaging/Reference/CGContext/Reference/reference.html#//apple_ref/c/func/CGContextClip" rel="noreferrer"> CGContextClip

そのため、現在の描画パスはグラフィックス状態の一部ではありません。だからここにあなたがしていることがあります:

  1. 描画パスを構築
  2. gstate を保存
  3. 現在の描画パスをクリッピング パスに追加します。現在の描画パスをクリア
  4. グラデーションを描く
  5. gstate を復元します (以前のクリッピング パスが復元されます。描画パスは空のままです)。
  6. ストロークなし

解決策は、パスを CGPath オブジェクトに描画し、クリッピングの前 (gstate の保存後) とストロークの前の両方に現在のパスとして追加することです。

また、これを外側のストロークにするか、内側のストロークにするか、中央のストロークにするかを決定する必要があります。中央揃えのストロークでは、クリップされていない状態でストロークします。内側のストロークは、クリッピングしながらストロークします。外側のストロークの場合は、パスを反転してから、クリップしてからストロークします。ストロークの半分を切り取るので、最後の 2 つのフォームの両方で線幅を 2 ​​倍にする必要があります。

を に変更するCGContextStrokePath(c)CGContextStrokeRect(c, rect)、ストロークが表示されます。

その関数は、ストロークする前に、その長方形のパスを現在の描画パスに追加するためです。

于 2010-02-01T20:14:18.857 に答える
0

ストローク上にグラデーションを描画するか、ストロークする領域をクリップします。

次の方がうまくいくと思います。

CGContextSaveGState(c);
CGContextClip(c);

//gradient drawing stuff

CGContextRestoreGState(c);
CGContextStrokePath(c);

もちろん、ストロークの色と幅も正しく設定する必要があります。

于 2010-02-01T14:27:39.037 に答える
0

わかりませんが、ストローク全体にグラデーションをペイントしているのではないでしょうか。

于 2010-02-01T14:21:53.797 に答える