【问题标题】:Adding a spacing between images in a UIScrollView在 UIScrollView 中的图像之间添加间距
【发布时间】:2011-02-25 20:41:06
【问题描述】:

如何在添加到 UIScrollView 的多个图像之间添加间隙/空间?

一个例子是照片应用程序,它在分页时图像之间有黑色间距。

【问题讨论】:

    标签: iphone


    【解决方案1】:

    我假设您知道如何在启用分页的情况下将图像添加到 UIScrollView。我还假设您想查看全屏照片,但是在滚动时,您希望它们之间有间隙。如果是,这是一种可能的解决方案...

    • 将间隙定义为 20 像素
    • UIScrollView 是全屏视图,iPhone 为 320x480
    • 将 UIScrollView 框架设置为 CGRectMake( 0, 0, 340, 480 ); // 340 = 320 + 20(间隙,这 20px 在屏幕外)
    • 将第一个图像帧设置为 CGRectMake(0,0,320,480);
    • 第二个图像帧到 CGRectMake(340, 0, 320, 480);
    • ... I-th image CGRectMake( 340 * I, 0, 320, 480 ) // I is index - 0..N-1
    • 将 UIScrollView 内容大小设置为 CGSizeMake(340 * N, 480) // N = 图片数量

    ...如果您不想缩放,只需要全屏、分页、有间隙滚动,这是一个非常快速的解决方案。

    【讨论】:

    • 像我这样的数学菜鸟的最佳答案。谢谢!
    • 这看起来应该可行,但对我来说,差距并没有滑出视野。有什么想法吗?
    【解决方案2】:

    这只是基础数学..

    您将 UIImageView 添加为子视图,并根据子视图的大小和滚动视图的 contentSize 计算您想要的空间。

    编辑:

    这基本上建立了一个画廊

    -(void)photosGallery
    {
        UIScrollView* scrollView = [[UIScrollView alloc] initWithFrame:(CGRect){.origin.x = 0.0f, .origin.y = 0.0f, .size.width = 320.0f, .size.height = 416.0f}];
        scrollView.contentSize = (CGSize){.width = view.frame.size.width, .height = 372.0f};
        scrollView.backgroundColor = [UIColor whiteColor];
        scrollView.showsVerticalScrollIndicator = NO;
        scrollView.showsHorizontalScrollIndicator = NO;
        /// Build gallery
        CGSize thumbSize = (CGSize){.width = 75.0f, .height = 75.0f};
        const CGFloat xSpace = (scrollView.frame.size.width - (thumbSize.width * kPictsPerRow)) / (kPictsPerRow + 1); // kPictsPerRow = Number of pictures in a row
        const CGFloat xInc = thumbSize.width + xSpace;
        const CGFloat yInc = thumbSize.height + 15.0f;
        CGFloat x = xSpace, y = 10.0f;
        for (NSUInteger i = kMaxPictures; i--;)
        {
            UIImageView* pv = [[UIImageView alloc] initWithFrame:(CGRect){.origin.x = x, .origin.y = y, .size = thumbSize}];
            [scrollView addSubview:pv];
            [pv release];
            x += xInc;
            const NSUInteger eor = i % kPictsPerRow;
    
            if (!eor)
                y += yInc, x = xSpace;
        }
        [scrollView release];
    }
    

    【讨论】:

    • 我知道,但是如何将间隙输入/添加到滚动视图中?如果将每个图像的子视图添加到滚动视图,那么该数学在哪里应用于滚动视图?它是如何添加的?
    • @Benj:我设置好了滚动视图,添加所有图像时我遇到的一个问题是效率。将所有图像加载到视图中需要一段时间。有没有最佳的方法来做到这一点?
    • 变化很大,可能很多。它是来自用户手机的一堆 ALAsset。我基本上重新创建了照片应用程序的功能,但遇到了一些效率问题。
    • 我想只加载可见图像,如果你有很多图像,在滚动时加载它们可能会更好。
    • 是的,我想是的。如何将滚动视图中的图像设置为自动旋转?
    【解决方案3】:

    只需要设置 UIImageVIew 的框架,它们之间有一些空间。例如,如果 scroll_view 是 UIScrollView 你可以这样做

    scroll_view.contentSize = CGSizeMake(1000,100);
    for (int i=0;i<10;i++){
        UIImageView *imv = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"some_image.png"]];
        CGRect frame = CGRectInset(CGRectMake(i * 100,0.0,100.0,100.0), 5.0, 4.0);
        imv.frame = frame;
        [scroll_view addSubview:imv];
    }
    

    这是一个粗略的例子,但说明了重点。通过插入 CGRect (CGRectInset),您可以在滚动视图中的图像之间获得一些空间。

    【讨论】:

      【解决方案4】:

      我必须在类似的应用程序中执行此操作,我的解决方案记录在此答案中(请注意,该问题与滚动视图无关,但所涉及的概念相似):PDF in UIWebView

      【讨论】:

        【解决方案5】:

        您可能正在寻找此代码:

        #define FRAME_WIDTH 330
        - (void)viewDidLoad {
            [super viewDidLoad];
        
            self.scrollView = [[UIScrollView alloc] initWithFrame:CGRectMake(0, 0, FRAME_WIDTH, self.view.bounds.size.height)];
            self.scrollView.bounces = YES;
            self.scrollView.pagingEnabled = YES;
        
            UIImageView *leftView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"2.png"]];
            leftView.frame = CGRectMake(0, 0, 320, self.view.bounds.size.height);
        
            UIImageView* centerView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"9.png"]];
            centerView.frame = CGRectMake(FRAME_WIDTH, 0, 320, self.view.bounds.size.height);
        
            UIImageView *rightView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"10.png"]];
            rightView.frame = CGRectMake(FRAME_WIDTH * 2, 0,320,self.view.bounds.size.height);
        
            [self.scrollView addSubview:leftView];
            [self.scrollView addSubview:centerView];
            [self.scrollView addSubview:rightView];
        
            [self.scrollView setContentSize:CGSizeMake(FRAME_WIDTH * 3, 0)];
            [self.scrollView setContentOffset:CGPointMake(FRAME_WIDTH, 0)];
        
            [self.view addSubview:self.scrollView];
        }
        

        看起来像 iOS 照片应用。此示例创建 3 个 ImageView。

        附上一个测试项目,你可以自己试试:Project

        【讨论】:

          【解决方案6】:

          为避免弄乱 UIScrollView 的框架,您可以继承 UIScrollView 并覆盖 layoutSubviews 以对每个页面应用偏移量。

          这个想法基于以下观察:

          1. 当 zoomScale !=1 时,在左/右边缘时偏移量为零
          2. 当 zoomScale ==1 时,偏移量在可见矩形中心时为零

          那么导出如下代码:

          - (void) layoutSubviews
          {
              [super layoutSubviews];
          
              // Find a reference point to calculate the offset:
              CGRect bounds = self.bounds;
              CGFloat pageGap = 8.f;
              CGSize pageSize = bounds.size;
              CGFloat pageWidth = pageSize.width;
              CGFloat halfPageWidth = pageWidth / 2.f;
              CGFloat scale = self.zoomScale;
              CGRect visibleRect = CGRectMake(bounds.origin.x / scale, bounds.origin.y / scale, bounds.size.width / scale, bounds.size.height / scale);
              CGFloat totalWidth = [self contentSize].width / scale;
              CGFloat scrollWidth = totalWidth - visibleRect.size.width;
              CGFloat scrollX = CGRectGetMidX(visibleRect) - visibleRect.size.width / 2.f;
              CGFloat scrollPercentage = scrollX / scrollWidth;
              CGFloat referencePoint = (totalWidth - pageWidth) * scrollPercentage + halfPageWidth;
          
              // (use your own way to get all visible pages, each page is assumed to be inside a common container)
              NSArray * visiblePages = [self visiblePages];
          
              // Layout each visible page:
              for (UIView * view in visiblePages)
              {
                  NSInteger pageIndex = [self pageIndexForView:view]; // (use your own way to get the page index)
          
                  // make a gap between pages
                  CGFloat actualPageCenter = pageWidth * pageIndex + halfPageWidth;
                  CGFloat distanceFromRefPoint = actualPageCenter - referencePoint;
                  CGFloat numOfPageFromRefPoint = distanceFromRefPoint / pageWidth;
                  CGFloat offset = numOfPageFromRefPoint * pageGap;
                  CGFloat pageLeft = actualPageCenter - halfPageWidth + offset;
          
                  view.frame = CGRectMake(pageLeft, 0.f, pageSize.width, pageSize.height);
              }
          }
          

          【讨论】:

            猜你喜欢
            • 2013-03-18
            • 1970-01-01
            • 2020-08-20
            • 1970-01-01
            • 1970-01-01
            • 2017-06-06
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多