2012-12-19 46 views
2

我有几行在两个不同的子类中复制的绘图代码。当我将这个绘图代码移动到它自己的类中,然后从drawRect中调用它时:它被调用,但它永远不会绘制到屏幕上。什么是正确的方法防止在两个不同的drawRect:方法中重复代码?如何防止2 drawRect:方法内的重复代码?

详情:我正在通过继承NSTableViewNSTableCellView进行自定义控制。我的绘图代码需要在drawRect:这两个子类中。

我创建了一个声明一个方法的NSObject的子类。这里是执行:

@implementation TNLChartDrawingExtras 

- (void)drawDividersInRect:(NSRect)rect startingAtDate:(NSDate *)startDate withZoomFactor:(NSNumber *)zoomFactor { 

    float pos = 0; 
    NSDate *currentDate = [startDate copy]; 

    while (pos < rect.size.width) { 

     //draw the vertical divider 
     NSBezierPath *linePath = [NSBezierPath bezierPathWithRect:NSMakeRect(pos, 0.0, 1.0, rect.size.height)]; 
     [[NSColor colorWithCalibratedWhite:0.85 alpha:0.5] set]; 
     [linePath fill]; 

     //increment the values for the next day 
     currentDate = [NSDate dateWithTimeInterval:86400 sinceDate:currentDate]; // add one day to the current date 
     pos = pos + (86400.0/ [zoomFactor floatValue]); 
    } 
} 

在我的NSTableView子类中,我为这个对象定义一个属性。然后在awakeFromNib我创建这个类的一个实例:

- (void)awakeFromNib { 
    self.extras = [[TNLChartDrawingExtras alloc] init]; 
} 

drawRect:我发这条短信:

- (void)drawRect:(NSRect)dirtyRect { 
    // more code here... 

    [self.extras drawDividersInRect:viewBounds startingAtDate:chart.startDate withZoomFactor:self.zoomFactor]; 
} 

被执行的代码,但该行是应该汲取不会出现。如果我将drawDividersInRect:...的代码放在drawRect:方法中,它可以正常工作。

+1

您应该添加一些代码,以便我们可以看到您正在尝试的内容。 – Matt

+0

你检查过'self.extras'不是'nil'吗?这将解释它。 – djromero

回答

1

如果我继续调试它,我原来的解决方案(在问题中描述)可能已经工作。不过,我认为更重要的问题是解决这个问题的正确方法是什么。在这里,我通过在项目中添加NSView类别来解决此问题:

我试图将自定义绘图代码添加到NSTableViewNSTableCellView。两者都是NSView的子类,所以我创建了一个NSView类别,并在那里添加了我的自定义绘图方法。现在我可以从两个子类中调用我的绘图方法。

+0

我同意你的解决方案。这利用了OOP范例和类继承。如果您以后需要添加其他类型的视图,您仍然可以访问该方法。维护和调试也更容易。 – Matt

+0

@MikeT迈克,你能帮我解决我的问题:http://stackoverflow.com/questions/39855349/how-to-make-2-contradictory-methods-work-in-drawrect – andy

0

没有看到任何你的代码,这听起来像你需要一个协议,这是一个与java语言中的接口相同的东西。协议是一系列可能需要使用一组不相关的类的一系列方法。例如,在像PhotoShop这样的绘图程序中,Rects,Oval和Images都是可以作为图层存储在.psd文档中的有效对象,但是,它们都共享特性,例如以特定方式更改对象属性的能力。一个例子是调整对象的不透明度或重新缩放对象大小等。访问用于缩放的对象属性或可以在不相关的对象类型之间共享的函数的方法需要协议。

它们本质上是.h文件,列出了方法。定义代码实现的.m文件可以在它的.h文件中存储标签。

// example of a class that acts as a protocol implementor 
@interface LayerObject: NSObject <Resizable> 

标签说,“我是名为X的协议中的一员,你可以找到一个/一些协议X在我的.m文件的方法。”您只需使用以下语法将协议导入所需的类:

// Declare protocol 
@protocol Resizable; 
// List methods wanted from protocol 
- id resizeRect: id layerObject; 

获取协议中定义的方法。

这里是一个网站,通过一个例子描述了协议: http://agilewarrior.wordpress.com/2012/03/19/simple-objective-c-protocol-example/

另一种解决方案是创建一个使用抽象类来把你在工作中给予的drawRect方法的类层次结构在这里,您可以。定义你正在使用的两个子类作为它们将继承drawRect方法代码的抽象类的子类,从而避免在两个单独的类中重复代码。

+0

不知道协议如何帮助我。我的协议基本上是一个承诺,一个班级将实施一种方法。我仍然需要在两个不同的类中实现该方法。 –

+0

@Mike T - 无法看到您的代码很难回答问题。我在回答底部提到了定义在层次结构中聘用的方法(即NSView)的替代解决方案。也许你应该在投票前阅读答案。 – Matt

+0

嗨马特 - 这不是我低估了你的答案。其实这是你的第二个解决方案,让我思考NSView,这是由我的子类继承的两个类。 –