2

私はこのように線を引きます:

- (void)drawRect:(CGRect)rect {

    _lineColor = [UIColor blackColor];

    [_lineColor setStroke];
    [_lineColor setFill];

    CGContextRef c = UIGraphicsGetCurrentContext();
    CGContextClearRect(c, rect);
    [[UIColor clearColor] setFill];
    CGContextAddRect(c, rect);
    CGContextSetLineWidth(c, 1);
    CGContextDrawPath(c, kCGPathFill);
    CGContextBeginPath(c);
    CGContextMoveToPoint(c, 0, 0);
    CGContextAddLineToPoint(c, x1, y1);
    CGContextStrokePath(c);  
}

しかし、私の線は幅が異なり、角度は90度または45度です。同じ幅の線を引く方法

4

1 に答える 1

0

ここでの効果をより目立たせる何かを作りました。コードは次のとおりです。

- (void)drawRect:(CGRect)rect
{
    CGContextRef c = UIGraphicsGetCurrentContext();

    // Get us a gray background
    CGContextSetFillColorWithColor(c, [[UIColor grayColor] CGColor]);
    CGContextFillRect(c, CGRectInfinite);

    CGContextSetStrokeColorWithColor(c, [[UIColor blackColor] CGColor]);

    CGContextSetLineWidth(c, 1.0);
    CGContextBeginPath(c);

    // Draw some lines at various angles
    for (CGFloat i = -10.; i <= 10.; i += 1.0)
    {
        CGContextMoveToPoint(c, CGRectGetMidX(self.bounds), CGRectGetMidY(self.bounds));
        CGContextAddLineToPoint(c, CGRectGetMidX(self.bounds) + i * 10., CGRectGetMidY(self.bounds) + 100);
    }

    CGContextStrokePath(c);
}

Retina デバイスでのそのコードの出力は次のとおりです (これは、標準の StackOverflow 形式で 100% で表示されるはずですが、フルサイズで確認できます)。

ライン

今ここに爆破されたその一部があります:

拡大

ここに表示されているのは、動作中のアンチエイリアスです。まず、垂直線は常に 2.0 ピクセルで、アンチエイリアシングはありません (ピクセル境界に描画すると仮定します)。次に、同じピクセル グリッドを使用して描画された 45 度の線について考え、ピタゴラスの定理を使用します。別の図を次に示します。

45度線

幅が最も狭い (つまり、線自体に垂直な次元で) 45 度の線は 1.414 ピクセルの幅で表示され、不透明な部分が最も広い (ぎざぎざのギャップ内のスペースを橋渡ししているほとんど透明なピクセルを数えない) となります。幅 2.828 ピクセルで表示されます。拡大すると、これらの線をアンチエイリアスするために行われている作業が、線の視覚的な外観にどのように影響しているかがわかります。

おそらく誰かがやってきて、アンチエイリアシングをオフにすることを提案するでしょうが、参考までに、それは光学効果をさらに悪化させます(ラスタライザーはカバレッジを持つすべてのピクセルを完全に不透明にするため):

AA をオフにしました

要するに、これは予想される動作であり、デフォルトのアンチエイリアシング コードでは提供されない望ましい光学的外観を実現するために各線の描画方法を調整する必要がある場合は、その作業を行うだけです。CoreGraphics には「すべての行を光学的に類似させる」設定はありません。一般的なケースでできる限りのことを行っています。より具体的なものが必要な場合は、あなた次第です。FWIW、多くの多くのアプリケーションは単にデフォルトを使用しており、人々は結果にかなり満足しているようです。そのため、これがアプリ内で本当に多くの追加作業を入れたい場所であるかどうかを自問するかもしれません.

私は思いつきました: あなたが効果を気に入るかどうかはわかりませんが、光学的な類似性を達成するための 1 つの可能なアプローチは、ピクセル境界ではなく垂直線を描くことです。これにより、それらもアンチエイリアスされたように見えます。これにより、(見方によっては)角度のあるアンチエイリアスされた線とより一貫して見えるようになる場合があります。これは次のようになります。

0.25 オフセット

これを行うと失われるのは、線の特定の「鮮明さ」です。ピクセル境界を引き離すには、コンテキストを X 方向に 0.25pt 移動することで最も簡単に実現できます (網膜の場合 -- 非網膜の場合、0.5pt で同様の効果があります)。

    CGContextTranslateCTM(c, 0.25, 0);

お役に立てれば。

于 2013-08-07T12:15:40.110 に答える