尝试使用 UIScrollView 创建自定义水平 UIPickerView - 如何像在 UIPickerView 中一样淡出边缘?

Posted

技术标签:

【中文标题】尝试使用 UIScrollView 创建自定义水平 UIPickerView - 如何像在 UIPickerView 中一样淡出边缘?【英文标题】:Trying to create a custom horizontal UIPickerView using UIScrollView - how do I fade the edges out like in UIPickerView? 【发布时间】:2013-11-05 13:30:20 【问题描述】:

ios 7 中,UIPickerViews 在靠近边缘时在文本上有很好的阴影:

如果我使用的是 UIScrollView,是否可以实现类似的效果,即边缘处的文本略微被阴影/混合到背景中?

【问题讨论】:

【参考方案1】:

请参阅 here 和 here 了解我对类似问题的回答。

我的解决方案是继承UIScrollView,并在layoutSubviews 方法中创建一个遮罩层。

以上答案中的代码也是here on github。

希望有帮助!

【讨论】:

Steph 的解决方案是迄今为止最干净的。【参考方案2】:

我对这个类做了类似的事情来淡化滚动选取框的左右边缘。比使用两张图片更轻松,因为您可以轻松调整大小或重新着色:

@interface MarqueeFadeOverlay : UIView
@property(assign, nonatomic) CGGradientRef gradientLayer;
- (id)initWithFrame:(CGRect)frame andEndFadeWidth:(float)fadeWidth andFadeBarColor:(UIColor *)color;
@end

@implementation MarqueeFadeOverlay 
  UIColor *fadeBarColor;
  float endFadeWidth;


- (id)initWithFrame:(CGRect)frame andEndFadeWidth:(float)fadeWidth andFadeBarColor:(UIColor *)color 
    self = [super initWithFrame:frame];
    if (self) 
        endFadeWidth = fadeWidth;
        fadeBarColor = color;
        [self setOpaque:NO];
    
    return self;


- (void)drawRect:(CGRect)rect 
    CGContextRef context = UIGraphicsGetCurrentContext();
    CGContextDrawLinearGradient(context, self.gradientLayer, CGPointMake(0.0, 0.0),
    CGPointMake(self.frame.size.width, 0.0), kCGGradientDrawsBeforeStartLocation);


- (CGGradientRef)gradientLayer 
    if (_gradientLayer == nil) 
        CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
        CGFloat *colorComponents = [self rgbaFrom:fadeBarColor];
        if (endFadeWidth == 0) endFadeWidth = 0.1;
        CGFloat locations[] = 0.0, endFadeWidth, 1.0 - endFadeWidth, 1.0;
        CGFloat colors[] = colorComponents[0], colorComponents[1], colorComponents[2], 1.00,
            colorComponents[0], colorComponents[1], colorComponents[2], 0,
            colorComponents[0], colorComponents[1], colorComponents[2], 0,
            colorComponents[0], colorComponents[1], colorComponents[2], 1.00;

        _gradientLayer = CGGradientCreateWithColorComponents(colorSpace, colors, locations, sizeof(colors) / (sizeof(colors[0]) * 4));
       CGColorSpaceRelease(colorSpace);
   
   return _gradientLayer;


-(CGFloat *)rgbaFrom:(UIColor *)color 
   CGColorRef colorRef = [color CGColor];
   return (CGFloat *) CGColorGetComponents(colorRef); 


您只需使用一个框架、一个介于 0 和 1 之间的渐变宽度以及与背景匹配的颜色来初始化一个,然后添加到父视图中。

【讨论】:

【参考方案3】:

我会为此放置两个自定义覆盖视图,您将它们放置在滚动视图的顶部。视图可以包含从全白渐变到 alpha 为 0 的预制图像,或者您可以使用 Core Graphics 或 CAGradientLayer 在代码中绘制图像。

如果您在视图上设置userInteractionEnabled = NO;,它们将不会干扰触摸处理。

【讨论】:

这不会导致渐变矩形吗?文本是上面屏幕截图中唯一混合的部分 这正是使用从 alpha=1 到 alpha=0 混合的渐变所达到的效果。 在文本上,而不是在任意矩形上。

以上是关于尝试使用 UIScrollView 创建自定义水平 UIPickerView - 如何像在 UIPickerView 中一样淡出边缘?的主要内容,如果未能解决你的问题,请参考以下文章

自定义 UIView 中的 UIScrollView 不滚动

在 UIScrollView 中仅水平缩放 UIView

用两个手指使用 UIScrollView 的自定义容器

如何在 UIScrollView 中绘制自定义形状

UIScrollView 或 UICollectionView 中的自定义滚动行为

如何在 ios 中使用自定义形状创建 uiscrollview?