QQList

本文详细介绍了如何采用MVC模式设计并实现一个QQ好友列表界面,包括模型层、视图层和控制器层的构建过程。通过定义自定义的数据模型类FUTHFriend和FUTHFriendGroup来封装好友信息,并利用自定义的视图类FUTHFriendCell展示好友列表,最终通过ViewController控制器整合所有组件,实现了一个动态更新的好友列表界面。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

思路:采用 MVC的思想来进行编写该界面


首先是模型:

//

//  FUTHFriend.h

//  QQ好友列表

//

//  Created by future on 15/7/23.

//  Copyright (c) 2015 future. All rights reserved.

//


#import <Foundation/Foundation.h>


@interface FUTHFriend : NSObject


@property (nonatomic,copy)NSString* name;

@property (nonatomic,copy)NSString* icon;

@property (nonatomic,copy)NSString* intro;

@property (nonatomic,assign,getter=isVip)BOOL vip;


+(instancetype)friendWithDict:(NSDictionary*)dict;

-(instancetype)initWithDict:(NSDictionary*)dict;



@end


//

//  FUTHFriend.m

//  QQ好友列表

//

//  Created by future on 15/7/23.

//  Copyright (c) 2015 future. All rights reserved.

//


#import "FUTHFriend.h"


@implementation FUTHFriend



+(instancetype)friendWithDict:(NSDictionary*)dict

{

    FUTHFriend* f = [[FUTHFriendalloc]initWithDict:dict];

    return  f;

}

-(instancetype)initWithDict:(NSDictionary*)dict{

    if (self = [superinit]) {

        [selfsetValuesForKeysWithDictionary:dict];

    }

    return self;

}


@end


#import <Foundation/Foundation.h>




@interface FUTHFriendGroup : NSObject


@property (nonatomic,copy)NSString* name;

@property (nonatomic,strong)NSArray* friends;

@property (nonatomic,assign)int online;

/**

 *  是否展开

 */

@property (nonatomic,assign,getter=isOpen)BOOL  open;


+(instancetype)groupWithDict:(NSDictionary*)dict;

-(instancetype)initWithDict:(NSDictionary*)dict;


@end


#import "FUTHFriendGroup.h"

#import "FUTHFriend.h"



@implementation FUTHFriendGroup


+(instancetype)groupWithDict:(NSDictionary*)dict{

    FUTHFriendGroup* f = [[FUTHFriendGroupalloc]initWithDict:dict];

    return  f;

}

-(instancetype)initWithDict:(NSDictionary*)dict{

    if (self = [superinit]) {

        //注入所以属性

        [selfsetValuesForKeysWithDictionary:dict];

        

        //特殊处理 friends

        NSMutableArray* mtArray = [NSMutableArrayarray];

        for (NSDictionary* dictin self.friends) {

            FUTHFriend* friend = [[FUTHFriendalloc] initWithDict:dict];

            [mtArray addObject:friend];

        }

        _friends = mtArray;

        

    }

    returnself;

}



@end





然后视图:

#import <UIKit/UIKit.h>


@classFUTHFriend;

@interface FUTHFriendCell : UITableViewCell


+ (instancetype)cellWithTableView:(UITableView*)tableView;


@property (nonatomic,strong)FUTHFriend* friendData;



@end


#import "FUTHFriendCell.h"

#import "FUTHFriend.h"


@implementation FUTHFriendCell


- (void)awakeFromNib {

    // Initialization code

}


- (void)setSelected:(BOOL)selected animated:(BOOL)animated {

    [super setSelected:selected animated:animated];


    // Configure the view for the selected state

}


+ (instancetype)cellWithTableView:(UITableView*)tableView{

    static NSString* ID = @"friends";

    FUTHFriendCell* cell = [tableViewdequeueReusableCellWithIdentifier:ID];

    if (cell == nil) {

        cell = [[FUTHFriendCellalloc] initWithStyle:UITableViewCellStyleSubtitlereuseIdentifier:ID];

    }

    return cell;

}


-(void)setFriendData:(FUTHFriend *)friendData{

    

    self.imageView.image = [UIImageimageNamed:friendData.icon];

    self.textLabel.text = friendData.name;

    self.detailTextLabel.text = friendData.intro;

}



@end




#import <UIKit/UIKit.h>

@classFUTHFriendGroup;



@protocol FUTHFriendGroupDelegate <NSObject>


-(void)headerViewDidClickedNameView;


@end


@interface FUTHHeaderView :UITableViewHeaderFooterView

@property (nonatomic,strong)FUTHFriendGroup* group;


@property (nonatomic,weak)id<FUTHFriendGroupDelegate> delegate;



+(instancetype)headerWithTableView:(UITableView*)tableView;


@end



#import "FUTHFriendGroup.h"

#import "FUTHHeaderView.h"


@interfaceFUTHHeaderView()


@property (nonatomic,weak)UILabel* countView;

@property (nonatomic,weak)UIButton* nameView;


@end


@implementation FUTHHeaderView


/*

某个控件出不来

 1.frame 的尺寸

 

 2hidden 是否为 yes

 

 3.有没有添加到父控件

 

 4.alpha 是否为<0.01

 

 5.被其他控件挡住了

 

 6.父控件的前面五个情况

 

 */



+(instancetype)headerWithTableView:(UITableView*)tableView{

    static NSString* ID = @"header";

    FUTHHeaderView* header = [tableViewdequeueReusableHeaderFooterViewWithIdentifier:ID];

    if (header == nil ) {

        header = [[FUTHHeaderViewalloc] initWithReuseIdentifier:ID];

    }

    return  header;

    

}


//在初始化方法中FUTHHeaderView frame\bounds 0

-(instancetype)initWithReuseIdentifier:(NSString *)reuseIdentifier{

    

    if (self = [superinitWithReuseIdentifier:reuseIdentifier]) {

        //add btn

        UIButton* nameView = [UIButtonbuttonWithType:UIButtonTypeCustom];

        //

//        nameView.frame = self.bounds;

        nameView.backgroundColor = [UIColorredColor];

       // [nameView setBackgroundColor:[UIColor redColor] forState:UIControlStateNormal];

        [nameView setImage:[UIImageimageNamed:@"buddy_header_arrow"]forState:UIControlStateNormal];

        [nameView setBackgroundImage:[UIImageimageNamed:@"buddy_header_bg"]forState:UIControlStateNormal];

        [nameView setBackgroundImage:[UIImageimageNamed:@"buddy_header_bg_highlighted"]forState:UIControlStateHighlighted];

        

       

        nameView.titleLabel.textAlignment =NSTextAlignmentLeft;

        [nameView setTitleColor:[UIColorblackColor] forState:UIControlStateNormal];

        

        //对齐方式

        nameView.contentHorizontalAlignment =UIControlContentHorizontalAlignmentLeft;

        //边距

        nameView.contentEdgeInsets =UIEdgeInsetsMake(0,10,0,0);

        nameView.titleEdgeInsets =UIEdgeInsetsMake(0,10,0,0);

       _nameView = nameView;

        //add click event

        [nameView addTarget:selfaction:@selector(nameViewClicked)forControlEvents:UIControlEventTouchUpInside];

        //设置按钮内部的 imageView的内容模式为居中

        nameView.imageView.contentMode =UIViewContentModeCenter;

        //不裁剪图片

        nameView.imageView.clipsToBounds =NO;

        

        [self.contentViewaddSubview:nameView];

     

        

        //add friend count

        UILabel* countlabel = [[UILabelalloc] init];

        countlabel.textColor = [UIColorblackColor];

        

        [self.contentViewaddSubview:countlabel];

        countlabel.textAlignment =NSTextAlignmentRight;

        _countView = countlabel;

    }

  

    returnself;

}


/**

 *  头部的点击事件

 *

 *  @return void

 */

-(void)nameViewClicked{

    _group.open = !_group.open;

    if ([_delegaterespondsToSelector:@selector(headerViewDidClickedNameView)]) {

        [_delegateheaderViewDidClickedNameView];

    }

    //在此调用不行,因为 reloadData会刷新控件

//    if (_group.isOpen) {

//        self.nameView.imageView.transform = CGAffineTransformMaker

//    }

}

/**

 *  当控件被加入的时候会自动调用

 */

-(void)didMoveToSuperview{

    

    if (_group.isOpen) {

        self.nameView.imageView.transform = CGAffineTransformMakeRotation(M_PI_2);

    } else{

        self.nameView.imageView.transform = CGAffineTransformMakeRotation(0);

    }

    

}


/**

 *  当一个控件的 frame发生改变的时候就会调用

 一般在这里布局内部的子控件的 frame

 *

 *  @return void

 */


-(void)layoutSubviews{

#warning  一定要调用 super 的方法

    [superlayoutSubviews];

    

    //set nameView

    _nameView.frame =self.bounds;

    

//set 好友的 frame

        CGFloat countY = 0;

        CGFloat countH =self.bounds.size.height;

        CGFloat countW = 150;;

        CGFloat countX = self.bounds.size.width -10 - countW;

        _countView.frame =CGRectMake(countX , countY, countW, countH);

    

}


-(void)setGroup:(FUTHFriendGroup *)group{

        //set nameView

    _group = group;

    [_nameViewsetTitle:group.nameforState:UIControlStateNormal];

    

    //set countView

    _countView.text = [NSStringstringWithFormat:@"%d/%d",_group.online,_group.friends.count];


    

}





@end





最后控制器:


#import <UIKit/UIKit.h>


@interface ViewController :UITableViewController



@end



#import "ViewController.h"

#import "FUTHFriend.h"

#import "FUTHFriendGroup.h"

#import "FUTHHeaderView.h"

#import "FUTHFriendCell.h"


@interfaceViewController ()<FUTHFriendGroupDelegate>


@property (nonatomic,strong)NSArray* groups;



@end


@implementation ViewController



#pragma mark -FriendGroup


-(NSArray*)groups{

    if (_groups ==nil) {

        

        NSArray* dictArray = [NSArrayarrayWithContentsOfFile:[[NSBundlemainBundle] pathForResource:@"friends.plist"ofType:nil]];

        NSMutableArray* groupArray = [NSMutableArrayarray];

        for (NSDictionary*dictin dictArray) {

            FUTHFriendGroup* group = [[FUTHFriendGroupalloc]initWithDict:dict];

            [groupArray addObject:group];

        }

        _groups = groupArray;

    }

    return_groups;

}




- (void)viewDidLoad {

    [superviewDidLoad];

    // Do any additional setup after loading the view, typically from a nib.

    self.tableView.sectionHeaderHeight =40;

 

}


-(BOOL)prefersStatusBarHidden{

    returnYES;

}


- (void)didReceiveMemoryWarning {

    [superdidReceiveMemoryWarning];

    // Dispose of any resources that can be recreated.

}


#pragma mark -TableDataSource


-(NSInteger)numberOfSectionsInTableView:(UITableView *)tableView{

    

    returnself.groups.count;

}


-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section{

   

    BOOL open = [self.groups[section]isOpen];

    if (open) {

     return [self.groups[section]friends].count;

    } else{

        return 0;

    }

    

}


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

    

       

    //set cell

    FUTHFriendGroup* group = self.groups[indexPath.section];

    FUTHFriend* friend = group.friends[indexPath.row];

    

    FUTHFriendCell* cell = [FUTHFriendCellcellWithTableView:tableView];

    //set data

    cell.friendData = friend;

    

    

    return cell;

}




//-(NSString*)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section{

//    return [self.groups[section] name];

//}


-(UIView*)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section{

    FUTHHeaderView* header = [FUTHHeaderViewheaderWithTableView:tableView];

    

    header.group = _groups[section];

    header.delegate = self;

    

    return header;

}





-(void)headerViewDidClickedNameView{

    

    [self.tableViewreloadData];

    

}















@end







评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值