IOS-Excel表格制作

仿照UITableView、UITableViewDataSource和UITableViewDelegate,支持自定义每一个小框内的视图。

视图:HJExcelView.h

//
//  HJExcelView.h
//  mehr 工作表
//
//  Created by 阳君 on 14-6-9.
//  Copyright (c) 2014年 Hjsj. All rights reserved.
//

#import <UIKit/UIKit.h>
#import "HJExcelViewCell.h"

@protocol HJExcelViewViewDelegate, HJExcelViewViewDataSource;


@interface HJExcelView : UIView <HJExcelViewViewCellDelegate>

/** 数据源代理*/
@property (nonatomic, assign) id <HJExcelViewViewDataSource> dataSource;
/** 界面代理*/
@property (nonatomic, assign) id <HJExcelViewViewDelegate>   delegate;

/** 边框颜色*/
@property (nonatomic, strong) UIColor *borderColor;
/** 边框大小(>0才有效果,默认为1.0)*/
@property (nonatomic)         CGFloat borderWidth;

/** cell到边框的间隙*/
@property (nonatomic) CGFloat  cellToBordeSpace;

/**
 *  刷新全部数据
 *
 *  @return void
 */
- (void)reloadData;

@end


@protocol HJExcelViewViewDelegate <NSObject>

@optional

/**
 *  点击cell
 *
 *  @param excelView HJExcelView
 *  @param indexPath 位置
 *
 *  @return void
 */
- (void)excelView:(HJExcelView *)excelView didSelectRowAtIndexPath:(NSIndexPath *)indexPath;

/**
 *  cell的行高,默认40,包含了borderWidth/2
 *
 *  @param excelView HJExcelView
 *  @param row       行
 *
 *  @return CGFloat
 */
- (CGFloat)excelView:(HJExcelView *)excelView heightForRow:(NSInteger)row;

/**
 *  cell的列宽,默认:60,包含了borderWidth/2
 *
 *  @param excelView HJExcelView
 *  @param section   列
 *
 *  @return CGFloat
 */
- (CGFloat)excelView:(HJExcelView *)excelView widthInSection:(NSInteger)section;

@end


@protocol HJExcelViewViewDataSource <NSObject>

@required

/**
 *  有多少行数据
 *
 *  @param excelView HJExcelView
 *
 *  @return NSInteger
 */
- (NSInteger)numberOfRowsInExcelView:(HJExcelView *)excelView;

/**
 *  有多少列数据
 *
 *  @param excelView HJExcelView
 *
 *  @return NSInteger
 */
- (NSInteger)numberOfSectionsInExcelView:(HJExcelView *)excelView;

/**
 *  生成cell
 *
 *  @param cell      已初始化的HJExcelViewCell
 *  @param indexPath 位置
 *
 *  @return HJExcelViewCell
 */
- (HJExcelViewCell *)excelViewCell:(HJExcelViewCell *)cell cellForRowAtIndexPath:(NSIndexPath *)indexPath;

@end

实现:HJExcelView.m

 //
//  HJExcelView.m
//  mehr
//
//  Created by 阳君 on 14-6-9.
//  Copyright (c) 2014年 Hjsj. All rights reserved.
//

#import "HJExcelView.h"
#import "HJExcelViewPoint.h"

@interface HJExcelView ()
{
@private
    /** 画版*/
    UIView *_boardView;
    /** 画布*/
    UIView *_contentView;
    
    /** 行列坐标点*/
    NSMutableArray *_cellRowArray, *_cellSectionArray;
}

@end


@implementation HJExcelView

- (id)initWithFrame:(CGRect)frame
{
    self = [super initWithFrame:frame];
    if (self) {
        _boardView = [[UIView alloc] initWithFrame:self.frame];
        [self addSubview:_boardView];
        // 手势操作
        // 移动
        UIPanGestureRecognizer *panRecognizer = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(handlePan:)];
        [_boardView addGestureRecognizer:panRecognizer];
    }
    return self;
}

#pragma mark  - 图形移动
- (void)handlePan:(UIPanGestureRecognizer *)recognizer
{
    // 取点
    CGPoint translatedPoint = [recognizer translationInView:_boardView];
    // 计算
    CGFloat x = recognizer.view.center.x + translatedPoint.x;
    CGFloat y = recognizer.view.center.y + translatedPoint.y;
    
    // 移动范围
    CGFloat contentWidth  = _contentView.frame.size.width / 2;
    CGFloat contentHeight = _contentView.frame.size.height / 2;
    CGFloat mainWidth  = self.frame.size.width / 2;
    CGFloat mainHeight = self.frame.size.height / 2;

    // 上移动
    if (translatedPoint.y < 0)
    {
        // 画布高度低于屏幕高度
        if (contentHeight < mainHeight)
        {
            // 禁止上边框离开屏幕边缘
            y = y > contentHeight ? y : contentHeight;
        }
    }
    // 下移动
    else
    {
        // 画布高度低于屏幕高度
        if (contentHeight < mainHeight)
        {
            // 禁止下边框离开屏幕边缘
            y = y < self.frame.size.height - contentHeight ? y : self.frame.size.height - contentHeight;
        }
    }
    
    // 左移动
    if (translatedPoint.x < 0)
    {
        // 画布高度低于屏幕高度
        if (contentWidth < mainWidth)
        {
            // 禁止左边框离开屏幕边缘
            x = x > contentWidth ? x : contentWidth;
        }

    }
    // 右移动
    else
    {
        if (contentWidth < mainWidth)
        {
            // 禁止右边框离开屏幕边缘
            x = x < self.frame.size.width - contentWidth ? x : self.frame.size.width - contentWidth;
        }
        
    }
    
    // 移动
    recognizer.view.center = CGPointMake(x, y);
    
    // 回归中心点
    [recognizer setTranslation:CGPointMake(0, 0) inView:_boardView];
}

#pragma mark - 获得边框颜色
- (UIColor *)borderColor
{
    // 是否设置为默认
    _borderColor = _borderColor ? _borderColor : [UIColor colorWithWhite:0.821 alpha:1.000];
    
    return _borderColor;
}

#pragma mark 获得边框大小
- (CGFloat)borderWidth
{
    // 是否设置为默认
    _borderWidth = _borderWidth > 0 ? _borderWidth : 1.0;
    
    return _borderWidth;
}

#pragma mark - 刷新数据
- (void)reloadData
{
    // 必须实现的代理方法
    if ([self.dataSource respondsToSelector:@selector(numberOfSectionsInExcelView:)] && [self.dataSource respondsToSelector:@selector(numberOfRowsInExcelView:)] && [self.dataSource respondsToSelector:@selector(excelViewCell:cellForRowAtIndexPath:)])
    {
        // 清空上次的画布
        [_contentView removeFromSuperview];
        _contentView = [[UIView alloc] initWithFrame:self.frame];
        [_boardView addSubview:_contentView];
        
        // 行
        NSInteger rows = [self.dataSource numberOfRowsInExcelView:self];
        // 列
        NSInteger sections = [self.dataSource numberOfSectionsInExcelView:self];
       
        CGFloat borderWidth = self.borderWidth / 2;
        
        // cell的大小位置
        CGRect frame = CGRectMake(borderWidth + self.cellToBordeSpace * 2, borderWidth + self.cellToBordeSpace * 2, 0, 0);
        
        _cellRowArray     = [NSMutableArray array];
        _cellSectionArray = [NSMutableArray array];
        
        NSInteger sumHeight = 0, sumWidth = 0;
        
        // 行操作
        for (int row = 0; row < rows; row ++ )
        {
            // 行高
            frame.size.height = [self heightForRow:row];
            // 保存行点
            HJExcelViewPoint *point = [HJExcelViewPoint excelViewPointWithX:frame.origin.x y:frame.origin.y];
            [_cellRowArray addObject:point];
            
            // 列操作
            for (int section = 0; section < sections; section ++ )
            {
                // 列宽
                frame.size.width = [self widthInSection:section];
                // 位置
                 NSIndexPath *indexPath = [NSIndexPath indexPathForRow:row inSection:section];
                
                 [self addExcelViewCellWithIndexPath:indexPath frame:frame];
                
                if (row == 0)
                {
                    // 保存列点
                    HJExcelViewPoint *point = [HJExcelViewPoint excelViewPointWithX:frame.origin.x y:frame.origin.y];
                    [_cellSectionArray addObject:point];
                }
                // 下一列位置
                frame.origin.x += frame.size.width + self.cellToBordeSpace * 2;
            }
            
            // 下一行第0个位置
            frame.origin.y += frame.size.height + self.cellToBordeSpace * 2;
            // 当出现最后一个点时,保存长度
            if (row == rows - 1)
            {
                sumHeight = frame.origin.y;
                sumWidth = frame.origin.x;
            }
            frame.origin.x = self.borderWidth / 2 + self.cellToBordeSpace * 2;
        }
        
        // 画边框
        HJExcelViewPoint *point;
        UIView *line;
        
        sumHeight -= self.cellToBordeSpace * 2;
        sumWidth  -= self.cellToBordeSpace * 2;
        
        // 画行
        for (int row = 0; row < rows; row ++ )
        {
            point = [_cellRowArray objectAtIndex:row];
            line = [[UIView alloc] initWithFrame:CGRectMake(point.x - borderWidth - self.cellToBordeSpace, point.y - borderWidth - self.cellToBordeSpace, sumWidth, self.borderWidth)];
            line.backgroundColor = self.borderColor;
            [_contentView addSubview:line];
        }

        // 画最后一行
        line = [[UIView alloc] initWithFrame:CGRectMake(point.x - borderWidth - self.cellToBordeSpace, sumHeight - borderWidth + self.cellToBordeSpace, sumWidth, self.borderWidth)];
        line.backgroundColor = self.borderColor;
        [_contentView addSubview:line];
        
        // 画列
        for (int section = 0; section < sections; section ++ )
        {
            point = [_cellSectionArray objectAtIndex:section];
            line = [[UIView alloc] initWithFrame:CGRectMake(point.x - borderWidth - self.cellToBordeSpace, point.y - borderWidth - self.cellToBordeSpace, self.borderWidth, sumHeight)];
            line.backgroundColor = self.borderColor;
            [_contentView addSubview:line];
        }
        // 画最后一列
        line = [[UIView alloc] initWithFrame:CGRectMake(sumWidth - borderWidth + self.cellToBordeSpace, point.y - borderWidth - self.cellToBordeSpace, self.borderWidth, sumHeight)];
        line.backgroundColor = self.borderColor;
        [_contentView addSubview:line];
        
        // 调整画板
        frame = _boardView.frame;
        frame.origin.x = - self.frame.size.width / 2;
        frame.origin.y = - self.frame.size.height / 2;
        frame.size.height = self.borderWidth + self.cellToBordeSpace + sumHeight + self.frame.size.height;
        frame.size.width  = self.borderWidth + self.cellToBordeSpace + sumWidth + self.frame.size.width;
        _boardView.frame = frame;
        
        // 调整画布
        frame = _contentView.frame;
        frame.origin.x = self.frame.size.width / 2;
        frame.origin.y = self.frame.size.height / 2;
        frame.size.height = self.borderWidth + self.cellToBordeSpace + sumHeight;
        frame.size.width  = self.borderWidth + self.cellToBordeSpace + sumWidth;
        _contentView.frame = frame;
    }
    
}

#pragma mark - cell的行高
- (CGFloat)heightForRow:(NSInteger)row
{
    if ([self.delegate respondsToSelector:@selector(excelView:heightForRow:)])
    {
        return [self.delegate excelView:self heightForRow:row];
    }
    else
    {
        return 44;
    }
}

#pragma mark cell的列宽
- (CGFloat)widthInSection:(NSInteger)section
{
    if ([self.delegate respondsToSelector:@selector(excelView:heightForRow:)])
    {
        return [self.delegate excelView:self widthInSection:section];
    }
    else
    {
        return 70;
    }
}

#pragma mark - 视图增加cell
- (void)addExcelViewCellWithIndexPath:(NSIndexPath *)indexPath frame:(CGRect)frame
{
    // 初始化cell
    HJExcelViewCell *cell = [[HJExcelViewCell alloc] initWithFrame:frame];
    // 通知主视图向cell中添加内容
    cell = [self.dataSource excelViewCell:cell cellForRowAtIndexPath:indexPath];
    // 调整大小
    cell.frame = frame;
    // 绑定位置
    cell.indexPath = indexPath;
    // 代理
    cell.excelViewDelegate = self;
    //  加到页面中
    [_contentView addSubview:cell];

}

#pragma mark - HJExcelViewViewCellDelegate
- (void)excelViewCell:(HJExcelViewCell *)excelViewCell didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
    // 判断是否开启可点击和实现回调
    if (excelViewCell.selected && [self.delegate respondsToSelector:@selector(excelView:didSelectRowAtIndexPath:)])
    {
        // 通知主视图,被点击
        [self.delegate excelView:self didSelectRowAtIndexPath:excelViewCell.indexPath];
    }
}

@end

每一个cell:HJExcelViewCell.h

//
//  HJExcelViewCell.h
//  mehr
//
//  Created by 阳君 on 14-6-10.
//  Copyright (c) 2014年 Hjsj. All rights reserved.
//

#import <UIKit/UIKit.h>

@protocol HJExcelViewViewCellDelegate;

@interface HJExcelViewCell : UIView

/** 是否可选,默认no关闭*/
@property (nonatomic) BOOL selected;

//以下属性,和HJExcelView通信,外部调用无用
/** 位置*/
@property (nonatomic, strong) NSIndexPath *indexPath;
@property (nonatomic, assign) id <HJExcelViewViewCellDelegate> excelViewDelegate;

@end




// 和HJExcelView通信,外部不用实现
@protocol HJExcelViewViewCellDelegate <NSObject>

@optional

/**
 *  点击cell
 *
 *  @param excelViewCell HJExcelViewCell
 *  @param indexPath 位置
 *
 *  @return void
 */
- (void)excelViewCell:(HJExcelViewCell *)excelViewCell didSelectRowAtIndexPath:(NSIndexPath *)indexPath;

@end

实现:HJExcelViewCell.m

//
//  HJExcelViewCell.m
//  mehr
//
//  Created by 阳君 on 14-6-10.
//  Copyright (c) 2014年 Hjsj. All rights reserved.
//

#import "HJExcelViewCell.h"

@implementation HJExcelViewCell

- (id)initWithFrame:(CGRect)frame
{
    self = [super initWithFrame:frame];
    if (self) {
        // Initialization code
    }
    return self;
}

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
{
    [self.excelViewDelegate excelViewCell:self didSelectRowAtIndexPath:self.indexPath];
}

@end


位置点:HJExcelViewPoint.h 

//
//  HJExcelViewPoint.h
//  mehr
//
//  Created by 阳君 on 14-6-10.
//  Copyright (c) 2014年 Hjsj. All rights reserved.
//

#import <Foundation/Foundation.h>

@interface HJExcelViewPoint : NSObject

/** 坐标x*/
@property (nonatomic) CGFloat x;
/** 坐标y*/
@property (nonatomic) CGFloat y;

/**
 *  生成坐标
 *
 *  @param x x
 *  @param y y
 *
 *  @return HJExcelViewPoint
 */
+ (id)excelViewPointWithX:(CGFloat)x y:(CGFloat)y;

@end


实现:HJExcelViewPoint.m 

//
//  HJExcelViewPoint.m
//  mehr
//
//  Created by 阳君 on 14-6-10.
//  Copyright (c) 2014年 Hjsj. All rights reserved.
//

#import "HJExcelViewPoint.h"

@implementation HJExcelViewPoint

+ (id)excelViewPointWithX:(CGFloat)x y:(CGFloat)y
{
    HJExcelViewPoint *point = [[[self class] alloc] init];
    
    point.x = x;
    point.y = y;
    
    return point;
}

@end

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值