UIView可以被复制吗?
只需使用这种方式
UIView* view2 = [view1 copy]; //view1 existed
这将导致模拟器无法启动这个应用程序。
尝试保留,
UIView* view2 = [view1 retain]; //view1 existed //modify view2 frame etc
对view2的任何修改将适用于view1,我明白,view2与view1共享相同的内存。
为什么不能复制UIView
? 是什么原因?
您的应用程序可能会崩溃,如下所示:
[UIView copyWithZone:]: unrecognized selector sent to instance 0x1c6280
原因是UIView没有实现复制协议,因此UIView中没有copyWithZone
select器。
这可能会为你工作…存档视图,然后马上取消存档。 这应该给你一个观点的深层副本:
id copyOfView = [NSKeyedUnarchiver unarchiveObjectWithData:[NSKeyedArchiver archivedDataWithRootObject:originalView]];
你可以做一个UIView扩展。 在下面的示例swift中,函数copyView返回一个AnyObject,所以你可以复制UIView的任何子类, 即 UIImageView。 如果你只想复制UIViews,你可以改变返回types为UIView。
//MARK: - UIView Extensions extension UIView { func copyView<T: UIView>() -> T { return NSKeyedUnarchiver.unarchiveObject(with: NSKeyedArchiver.archivedData(withRootObject: self)) as! T } }
用法示例:
let sourceView = UIView() let copiedView = sourceView.copyView()
对于swift3.0.1:
extension UIView{ func copyView() -> AnyObject{ return NSKeyedUnarchiver.unarchiveObject(with: NSKeyedArchiver.archivedData(withRootObject: self))! as AnyObject } }
UIView
没有实现NSCoping
协议,请参阅UIView.h中的声明:
@interface UIView : UIResponder <NSCoding, UIAppearance, UIAppearanceContainer, UIDynamicItem, UITraitEnvironment, UICoordinateSpace, UIFocusEnvironment>
所以,如果我们想要一个像方法一样的copy
,我们需要在一个类别中实现NSCoping
协议。
你可以使方法如下所示:
-(UILabel*)copyLabelFrom:(UILabel*)label{ //add whatever needs to be copied UILabel *newLabel = [[UILabel alloc]initWithFrame:label.frame]; newLabel.backgroundColor = label.backgroundColor; newLabel.textColor = label.textColor; newLabel.textAlignment = label.textAlignment; newLabel.text = label.text; newLabel.font = label.font; return [newLabel autorelease]; }
那么你可以设置你的伊娃到返回值,并像这样保留它:
myLabel = [[self copyLabelFrom:myOtherLabel] retain];