我创建了一个UIView
子类,它的图层使用CAGradientLayer
。这工作正常。现在我想在渐变的末尾绘制一条线(用作分隔符)。我以为我可以使用这个方法drawRect
:用CAGradientLayer作为后备存储在UIView上画线
public class GradientView : UIView
{
// accessors
private CAGradientLayer gradientLayer {
// read-only
get { return (CAGradientLayer)this.Layer; }
}
public CGColor[] Colors {
// set the colors of the gradient layer
get { return this.gradientLayer.Colors; }
set { this.gradientLayer.Colors = value; }
}
[Export ("layerClass")]
public static Class LayerClass()
{
// use a different Core Animation layer for its backing store
// normally a CALayer is used for a UIView
return new Class (typeof(CAGradientLayer));
}
public override void Draw (RectangleF rect)
{
PointF pointA = new PointF (0, rect.Height);
PointF pointB = new PointF (rect.Width, rect.Height);
CAShapeLayer line = new CAShapeLayer();
UIBezierPath linePath = new UIBezierPath();
linePath.MoveTo (pointA);
linePath.AddLineTo(pointB);
line.Path = linePath.CGPath;
line.FillColor = null;
line.Opacity = 1.0f;
line.StrokeColor = UIColor.Black.CGColor;
this.gradientLayer.AddSublayer (line);
base.Draw (rect);
}
}
但我得到一个黑色的背景。我可以使用drawRect
吗?或者我如何在其上添加一行?
我使用C#作为语言,但您也可以在Objective-C中提供您的解决方案。自动布局确定GradientView
的大小,我的旧解决方案也适应方向更改。
编辑:
我试了一下西里尔说:
public class GradientView : UIView
{
// accessors
private CAShapeLayer line;
private CAGradientLayer gradientLayer {
// read-only
get { return (CAGradientLayer)this.Layer; }
}
public CGColor[] Colors {
// set the colors of the gradient layer
get { return this.gradientLayer.Colors; }
set { this.gradientLayer.Colors = value; }
}
public GradientView()
{
PointF pointA = new PointF (0, this.Bounds.Height);
PointF pointB = new PointF (this.Bounds.Width, this.Bounds.Height);
line = new CAShapeLayer();
UIBezierPath linePath = new UIBezierPath();
linePath.MoveTo (pointA);
linePath.AddLineTo(pointB);
line.Path = linePath.CGPath;
line.FillColor = null;
line.Opacity = 1.0f;
line.StrokeColor = UIColor.Black.CGColor;
line.LineWidth = 1.0f;
this.gradientLayer.AddSublayer (line);
}
[Export ("layerClass")]
public static Class LayerClass()
{
// use a different Core Animation layer for its backing store
// normally a CALayer is used for a UIView
return new Class (typeof(CAGradientLayer));
}
public override void LayoutSubviews()
{
PointF pointA = new PointF (0, this.Bounds.Height-2);
PointF pointB = new PointF (this.Bounds.Width, this.Bounds.Height-2);
UIBezierPath linePath = new UIBezierPath();
linePath.MoveTo (pointA);
linePath.AddLineTo(pointB);
line.Path = linePath.CGPath;
base.LayoutSubviews();
}
}
这似乎做我想做的只是行不薄的发际线。是CAShapeLayer
不适合这个吗?
解决方案:
当然有可能使用CAShapeLayer
,但如果我必须设置事情drawRect
,然后我彻底划清我行那里。现在对我来说,解决方案看起来像下面这样:
public class GradientView : UIView
{
// accessors
private CAShapeLayer line;
private CAGradientLayer gradientLayer {
// read-only
get { return (CAGradientLayer)this.Layer; }
}
public CGColor[] Colors {
// set the colors of the gradient layer
get { return this.gradientLayer.Colors; }
set { this.gradientLayer.Colors = value; }
}
public GradientView()
{
this.BackgroundColor = UIColor.Clear;
}
[Export ("layerClass")]
public static Class LayerClass()
{
// use a different Core Animation layer for its backing store
// normally a CALayer is used for a UIView
return new Class (typeof(CAGradientLayer));
}
public override void Draw (RectangleF rect)
{
base.Draw (rect);
// get graphics context
CGContext context = UIGraphics.GetCurrentContext();
// start point
context.MoveTo (0, rect.Height);
// end point
context.AddLineToPoint (rect.Width, rect.Height);
context.SetLineWidth (1.0f);
context.SetShouldAntialias(false);
// draw the path
context.DrawPath (CGPathDrawingMode.Stroke);
}
感谢您的回复。我尝试了你所说的和它的工作原理。但有一个问题:我怎样才能用CAShapeLayer绘制一条细线? – testing 2014-12-09 12:28:10
关于SO的许多问题已经解决了这个问题:http://stackoverflow.com/questions/21515451/draw-a-line-with-a-calayer,http://stackoverflow.com/questions/21515451/drawa-a-一行一行... – Cyrille 2014-12-09 13:14:30
另一个问题:为什么'UIView'在我实现'drawRect'时得到黑色背景?似乎我无法关闭消除锯齿而没有获取当前的图形上下文(例如[禁用UIBezierPath的抗锯齿](http://stackoverflow.com/questions/15417410/disable-anti-aliasing-for-uibezierpath) )。但据我所知,当前的图形上下文只能在'drawRect'中使用,我再次无法实现。 – testing 2014-12-09 13:18:31