其他角度的线宽

时间:2013-08-05 04:39:28

标签: ios objective-c core-graphics line

我画这样的一行:

- (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度。如何画出相同宽度的线

1 个答案:

答案 0 :(得分: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);
}

以下是视网膜设备上该代码的输出:(这应该以标准StackOverflow格式显示为100%,但您可以查看它的全尺寸以确定)

Lines

现在这里有一个被炸毁的部分:

Enlargement

你在这里看到的是工作中的抗锯齿。对于初学者来说,垂直线始终为2.0像素,没有抗锯齿(假设您在像素边界上绘制它)。现在考虑使用相同像素网格绘制的45度线,并使用毕达哥拉斯定理。这是另一个图表:

45 deg line

在它最窄处(即垂直于线本身的尺寸),45度线将出现1.414px宽,并且在其最宽的不透明部分(不计算在锯齿状间隙中桥接空间的大部分透明像素)它会出现2.828像素差异。当炸毁时,您可以看到正在对这些线路进行抗锯齿处理的工作如何影响线条的光学外观。

有人可能会出现并建议您关闭抗锯齿,但作为参考,这会使光学效果更糟(因为那时光栅化器将使每个像素都覆盖范围完全不透明):

AA turned off

简而言之,这是预期的行为,如果您需要调整绘制每条线的方式以获得默认抗锯齿代码所不能提供的某些所需的光学外观,那么您只需要完成这项工作。在CoreGraphics中没有“让我的所有线条在光学上相似”的设置 - 他们已经为一般情况尽了最大努力,如果你需要更具体的东西,那就取决于你。 FWIW,许多应用程序只使用默认设置,人们似乎对结果非常满意,所以你可能会问自己这是否真的是你应用程序中想要放入一堆额外工作的地方。

我想到了:我不确定你会喜欢这种效果,但实现光学相似性的一种可能方法可能是在像素边界上绘制而不是的垂直线。这将使它们也出现消除锯齿,这取决于你如何看待它可能使它们看起来与成角度的抗锯齿线更加一致。这是看起来像:

offset by 0.25

你失去了这样做是对线条的某种“清脆”。通过在X方向上翻译上下文0.25pt(对于非视网膜,对于非视网膜,0.5pt将具有类似的效果),可以最容易地实现像素边界的绘制,如下所示:

    CGContextTranslateCTM(c, 0.25, 0);

希望这有帮助。