Re: Problem drawing outside of drawRect: in a custom table cell
Re: Problem drawing outside of drawRect: in a custom table cell
- Subject: Re: Problem drawing outside of drawRect: in a custom table cell
- From: Corbin Dunn <email@hidden>
- Date: Wed, 10 Dec 2008 08:46:09 -0800
On Dec 10, 2008, at 2:44 AM, Graham Cox wrote:
I need to draw outside of the usual drawRect: method (no really, I
do!)
The reason is that I have a custom cell that is used in a table/
outline view that draws a colour swatch. When clicked it pops up a
menu of colours so the user can choose another colour. While
tracking the menu, the cell shows the colour in the menu that the
mouse is over. When the mouse is released, the cell sends the chosen
colour to the table's datasource as usual.
The drawing of the colour while tracking the menu needs to take
place outside the drawRect: mechanism. Why? Because the host view is
a table, and I need to avoid it reloading the cell from the
datasource while I'm tracking the menu. If I invalidate the table
view, it will redraw the entire row. That would be OK if I could
rely on it to draw only my row, but in some circumstances I have
found that it doesn't, but redraws the whole table (for example
after editing a text cell, for some reason any
setNeedsDisplayInRect: on a small part of the table causes the whole
table to reload).
There are various reasons why this happens; for one, the focus ring
may bleed into the rect that was invalidated. But, as you have
noticed, you should not rely on invalidating just a small portion and
hoping only that portion should redraw.
I think it is still correct to invalidate your cell's rect, and have
the table redraw (potentially redrawing everything).
,,,......
Maybe it s a graphics context problem? I have tried always setting
the current context to the view's window but that stops it from ever
working (which may be a clue). Anyone spot anything I'm doing or not
doing here?
Also, if you feel tempted to advise me not to do it this way,
believe me, I have exhaustively investigated that route, which has
proven even more problematic, because there's insufficient fine
control over what the tableview itself does in its own drawRect:
method. So far this approach is the cleanest by far.
I think you should try another approach. Go back to invalidating the
rect of the cell that you want to redraw. Essentially, you want one
cell to maintain specific state while you are doing something else.
There is one easy approach to do this, which is to maintain a copy of
the cell while you are showing your special menu, and use that cell to
draw *just* that one particular row/column.
General steps:
1. Save off the row/column
2. Copy the cell at that row/column when showing your menu
3. Always return that copied cell from the delegate method:
- (NSCell *)tableView:(NSTableView *)tableView dataCellForTableColumn:
(NSTableColumn *)tableColumn row:(NSInteger)row
AVAILABLE_MAC_OS_X_VERSION_10_5_AND_LATER;
else, return [tableColumn dataCell].
4. Don't update the properties for that row/column in -willdisplaycell
5. Update the colors of that copied cell when your menu changes state
6. Drop the copied cell when your menu goes away.
Another approach would be something similar to this great example:
<http://developer.apple.com/samplecode/PhotoSearch/>
.corbin
_______________________________________________
Cocoa-dev mailing list (email@hidden)
Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden