代码之家  ›  专栏  ›  技术社区  ›  Mick Walker

iPhone UITableView-删除按钮

  •  27
  • Mick Walker  · 技术社区  · 15 年前

    我正在使用的“刷卡删除”功能 UITableView .

    问题是我使用的是定制的 UITableViewCell 它是在

    - (UITableViewCell *)tableView:(UITableView *)aTableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
    

    我需要改变删除按钮的位置(只需将其向左移动10px左右),我该怎么做呢?

    以下是我创建单元格的现有代码:

    - (UITableViewCell *)tableView:(UITableView *)aTableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
    {
        NSLog(@"cellForRowAtIndexPath");
    #if USE_CUSTOM_DRAWING
        const NSInteger TOP_LABEL_TAG = 1001;
        const NSInteger BOTTOM_LABEL_TAG = 1002;
        UILabel *topLabel;
        UILabel *bottomLabel;
    #endif
    
        static NSString *CellIdentifier = @"Cell";
        UITableViewCell *cell = [aTableView dequeueReusableCellWithIdentifier:CellIdentifier];
        if (cell == nil)
        {
            //
            // Create the cell.
            //
            cell =
            [[[UITableViewCell alloc]
              initWithFrame:CGRectZero
              reuseIdentifier:CellIdentifier]
             autorelease];
    
    #if USE_CUSTOM_DRAWING
    
    
            const CGFloat LABEL_HEIGHT = 20;
            UIImage *image = [UIImage imageNamed:@"trans_clock.png"];
    
            //
            // Create the label for the top row of text
            //
            topLabel =
            [[[UILabel alloc]
              initWithFrame:
              CGRectMake(
                         image.size.width + 2.0 * cell.indentationWidth,
                         0.5 * (aTableView.rowHeight - 2 * LABEL_HEIGHT),
                         aTableView.bounds.size.width -
                         image.size.width - 4.0 * cell.indentationWidth
                         ,
                         LABEL_HEIGHT)]
             autorelease];
            [cell.contentView addSubview:topLabel];
    
            //
            // Configure the properties for the text that are the same on every row
            //
            topLabel.tag = TOP_LABEL_TAG;
            topLabel.backgroundColor = [UIColor clearColor];
            topLabel.textColor = fontColor;
            topLabel.highlightedTextColor = [UIColor colorWithRed:1.0 green:1.0 blue:0.9 alpha:1.0];
            topLabel.font = [UIFont systemFontOfSize:[UIFont labelFontSize]];
    
            //
            // Create the label for the top row of text
            //
            bottomLabel =
            [[[UILabel alloc]
              initWithFrame:
              CGRectMake(
                         image.size.width + 2.0 * cell.indentationWidth,
                         0.5 * (aTableView.rowHeight - 2 * LABEL_HEIGHT) + LABEL_HEIGHT,
                         aTableView.bounds.size.width -
                         image.size.width - 4.0 * cell.indentationWidth
                         ,
                         LABEL_HEIGHT)]
             autorelease];
            [cell.contentView addSubview:bottomLabel];
    
            //
            // Configure the properties for the text that are the same on every row
            //
            bottomLabel.tag = BOTTOM_LABEL_TAG;
            bottomLabel.backgroundColor = [UIColor clearColor];
            bottomLabel.textColor = fontColor;
            bottomLabel.highlightedTextColor = [UIColor colorWithRed:1.0 green:1.0 blue:0.9 alpha:1.0];
            bottomLabel.font = [UIFont systemFontOfSize:[UIFont labelFontSize] - 2];
    
            //
            // Create a background image view.
            //
            cell.backgroundView =
            [[[UIImageView alloc] init] autorelease];
            cell.selectedBackgroundView =
            [[[UIImageView alloc] init] autorelease];
    #endif
        }
    
    #if USE_CUSTOM_DRAWING
        else
        {
            topLabel = (UILabel *)[cell viewWithTag:TOP_LABEL_TAG];
            bottomLabel = (UILabel *)[cell viewWithTag:BOTTOM_LABEL_TAG];
        }
        topLabel.text  = @"Example Text";
        topLabel.textColor = fontColor;
    
        bottomLabel.text = @"More Example Text";
        bottomLabel.textColor = fontColor;
    
        //
        // Set the background and selected background images for the text.
        // Since we will round the corners at the top and bottom of sections, we
        // need to conditionally choose the images based on the row index and the
        // number of rows in the section.
        //
        UIImage *rowBackground;
        UIImage *selectionBackground;
        NSInteger sectionRows = [aTableView numberOfRowsInSection:[indexPath section]];
        NSInteger row = [indexPath row];
        if (row == 0 && row == sectionRows - 1)
        {
            rowBackground = [UIImage imageNamed:@"topAndBottomRow.png"];
            selectionBackground = [UIImage imageNamed:@"topAndBottomRowSelected.png"];
        }
        else if (row == 0)
        {
            rowBackground = [UIImage imageNamed:@"topRow.png"];
            selectionBackground = [UIImage imageNamed:@"topRowSelected.png"];
        }
        else if (row == sectionRows - 1)
        {
            rowBackground = [UIImage imageNamed:@"bottomRow.png"];
            selectionBackground = [UIImage imageNamed:@"bottomRowSelected.png"];
        }
        else
        {
            rowBackground = [UIImage imageNamed:@"middleRow.png"];
            selectionBackground = [UIImage imageNamed:@"middleRowSelected.png"];
        }
        ((UIImageView *)cell.backgroundView).image = rowBackground;
        ((UIImageView *)cell.selectedBackgroundView).image = selectionBackground;
    
        cell.imageView.image = [UIImage imageNamed:@"Example_Image.png"];
    #else
        cell.text = @"Example";
    #endif
        return cell;
    }
    
    6 回复  |  直到 10 年前
        1
  •  23
  •   Jasarien    14 年前

    我的密码对我不起作用。但这是可行的。

    - (void)willTransitionToState:(UITableViewCellStateMask)state {
    
        [super willTransitionToState:state];
    
        if ((state & UITableViewCellStateShowingDeleteConfirmationMask) == UITableViewCellStateShowingDeleteConfirmationMask) {
    
            for (UIView *subview in self.subviews) {
    
                if ([NSStringFromClass([subview class]) isEqualToString:@"UITableViewCellDeleteConfirmationControl"]) {             
    
                    subview.hidden = YES;
                    subview.alpha = 0.0;
                }
            }
        }
    }
    
    - (void)didTransitionToState:(UITableViewCellStateMask)state {
    
        [super didTransitionToState:state];
    
        if (state == UITableViewCellStateShowingDeleteConfirmationMask || state == UITableViewCellStateDefaultMask) {
            for (UIView *subview in self.subviews) {
    
                if ([NSStringFromClass([subview class]) isEqualToString:@"UITableViewCellDeleteConfirmationControl"]) {
    
                    UIView *deleteButtonView = (UIView *)[subview.subviews objectAtIndex:0];
                    CGRect f = deleteButtonView.frame;
                    f.origin.x -= 20;
                    deleteButtonView.frame = f;
    
                    subview.hidden = NO;
    
                    [UIView beginAnimations:@"anim" context:nil];
                    subview.alpha = 1.0;
                    [UIView commitAnimations];
                }
            }
        }
    }
        2
  •  58
  •   Paras Joshi    12 年前

    对我来说,解决这个问题的最好办法是 -(void)layoutSubviews 在里面 MyCell:UITableViewCell

    在这里,您不仅可以看到“删除”按钮的自定义位置,还可以重新定位“编辑”和“重新排序”控件 编辑 模式

    - (void)layoutSubviews
    {
        [super layoutSubviews];
    
        [UIView beginAnimations:nil context:NULL];
        [UIView setAnimationBeginsFromCurrentState:YES];
        [UIView setAnimationDuration:0.0f];
    
        for (UIView *subview in self.subviews) {
    
    
            if ([NSStringFromClass([subview class]) isEqualToString:@"UITableViewCellDeleteConfirmationControl"]) { 
                CGRect newFrame = subview.frame;
                newFrame.origin.x = 200;
                subview.frame = newFrame;
            }
            else if ([NSStringFromClass([subview class]) isEqualToString:@"UITableViewCellEditControl"]) {             
                CGRect newFrame = subview.frame;
                newFrame.origin.x = 100;
                subview.frame = newFrame;
            }
            else if ([NSStringFromClass([subview class]) isEqualToString:@"UITableViewCellReorderControl"]) {             
                CGRect newFrame = subview.frame;
                newFrame.origin.x = 200;
                subview.frame = newFrame;
            }
        }
        [UIView commitAnimations];
    }
    
        3
  •  2
  •   Ethan    15 年前

    我无法更改“删除”按钮的实际外观,但您可以更改文本。也许你可以用这个来达到你想要的效果?

    查看以下成员 UITableViewDelegate 协议:

    - (NSString *)tableView:(UITableView *)tableView titleForDeleteConfirmationButtonForRowAtIndexPath:(NSIndexPath *)indexPath
    

    此外,还可以通过子类化来检测何时显示“删除”按钮。 UITableViewCell 并覆盖以下内容:

    - (void)willTransitionToState:(UITableViewCellStateMask)state
    - (void)didTransitionToState:(UITableViewCellStateMask)state
    

    对于其中任何一个,状态掩码都将 UITableViewCellStateShowingDeleteConfirmationMask 当显示“删除”按钮时。

    希望这些线索能为你指明正确的方向。

        4
  •  2
  •   Stefan    12 年前

    我使用的解决方案乍一看似乎有点黑客,但却能做到这一点,而且不依赖于未注册的API:

    /**
     * Transition to state
     */
    -(void)willTransitionToState:(UITableViewCellStateMask)state {
    
        if(state & UITableViewCellStateShowingDeleteConfirmationMask)
            _deleting = YES;
        else if(!(state & UITableViewCellStateShowingDeleteConfirmationMask))
            _deleting = NO;
        [super willTransitionToState:state];
    
    }
    
    /**
     * Reset cell transformations
     */
    -(void)resetCellTransform {
    
        self.transform = CGAffineTransformIdentity;
        _background.transform = CGAffineTransformIdentity;
        _content.transform = CGAffineTransformIdentity;
    }
    
    /**
     * Move cell around if we are currently in delete mode
     */
    -(void)updateWithCurrentState {
    
        if(_deleting) {
    
            float x = -20;
            float y = 0;
            self.transform = CGAffineTransformMakeTranslation(x, y);
            _background.transform = CGAffineTransformMakeTranslation(-x, -y);
            _content.transform = CGAffineTransformMakeTranslation(-x, -y);
        }
    }
    
    -(void)setFrame:(CGRect)frame {
    
        [self resetCellTransform];
        [super setFrame:frame];
        [self updateWithCurrentState];
    }
    
    -(void)layoutSubviews {
    
        [self resetCellTransform];
        [super layoutSubviews];
        [self updateWithCurrentState];
    }
    

    基本上,这改变了细胞的位置,重新调整了可见的部分。 willTransitionOnState只设置一个实例变量,指示单元格是否处于删除模式。需要覆盖setframe来支持将手机旋转到横向,反之亦然。 其中,background是我的单元格的背景视图,content是添加到单元格的content view中的视图,包含所有标签等。

        5
  •  1
  •   slf    15 年前

    我不知道“把删除按钮向左移动10px”的方法。但是,您可以通过监听 willTransitionToState: 来自A的消息 UITableViewCell 子类见 here .

    引用文档:

    UITableViewCell的子类可以 实现此方法以设置动画 单元格的其他更改 正在更改状态。uiTableView单元格 每当单元格 状态之间的转换,例如 从正常状态(默认)到 编辑模式。自定义单元格可以设置 向上定位任何新视图 以新状态显示。细胞 然后接收layoutSubviews消息 (uiview)在其中可以定位 这些新观点 新状态的位置。 子类在以下情况下必须始终调用super 重写此方法。

    你要找的是 UITableViewCellStateShowingDeleteConfirmationMask 值。这是创建UITableViewCell子类可能更好的时候之一,因此从控制器中,您只是创建自定义单元的一个实例。这样细胞就可以像 animateLeft animateRight 并处理调整自身子视图的内部工作。

        6
  •  0
  •   iwat    15 年前

    我不知道最终的解决方案,但就我而言,下面的代码可能有用。

    // subclass UITableViewCell
    
    - (void)willTransitionToState:(UITableViewCellStateMask)state
    {
        [super willTransitionToState:state];
    
        if ((state & UITableViewCellStateShowingDeleteConfirmationMask) == UITableCellStateShowingDeleteConfirmationMask)
        {
            for (UIView *subview in self.subviews)
            {
                if ([NSStringFromClass([subview class]) isEqualToString:@"UITableViewCellDeleteConfirmationControl"])
                {
                    subview.hidden = YES;
                    subview.alpha = 0;
                }
            }
        }
    }
    
    - (void)didTransitionToState:(UITableViewCellStateMask)state
    {
        [super willTransitionToState:state];
    
        if ((state & UITableViewCellStateShowingDeleteConfirmationMask) == UITableCellStateShowingDeleteConfirmationMask)
        {
            for (UIView *subview in self.subviews)
            {
                if ([NSStringFromClass([subview class]) isEqualToString:@"UITableViewCellDeleteConfirmationControl"])
                {
                    subview.frame = CGRectMake(subview.frame.origin.x - 10, subview.frame.origin.y, subview.frame.size.width, subview.frame.size.height);
                    subview.hidden = NO;
    
                    [UIView beginAnimations:@"anim" context:nil];
                    subview.alpha = 1;
                    [UIView commitAnimations];
                }
            }
        }
    }