Re: NSTableView editing problem [Was: Next stable release?]

2008-06-09 Thread Fred Kiefer

Matt Rice wrote:

On Sun, Jun 8, 2008 at 10:57 AM, Fred Kiefer [EMAIL PROTECTED] wrote:

I was completely wrong here. The problem is at a totally different place.
Look at the code in NSTextFieldsCell that Nicola changed a few months ago:



Ahh, yes changing the below fixes it here i was confused because it is
asked to redraw the edited cell frame, but in the case that it is, the
code is doing what it should by not redrawing.


- (void) drawInteriorWithFrame: (NSRect)cellFrame inView:
(NSView*)controlView
{
 /* Do nothing if there is already a text editor doing the drawing;
  * otherwise, we draw everything twice.  That is bad if there are
  * any transparency involved (eg, even an anti-alias font!) because
  * if the semi-transparent pixels are drawn over themselves they
  * become less transparent (eg, an anti-alias font becomes darker
  * and gives the impression of being bold).
  */
 if (([controlView respondsToSelector: @selector(currentEditor)] == NO)
 || ([(NSTextField *)controlView currentEditor] == nil))
   {
 if (_textfieldcell_draws_background)
   {
 if ([self isEnabled])
   {
 [_background_color set];
   }
 else
   {
 [[NSColor controlBackgroundColor] set];
   }
 NSRectFill([self drawingRectForBounds: cellFrame]);
   }

 [super drawInteriorWithFrame: cellFrame inView: controlView];
   }
}

This basically means that a text field cell will only draw itself, when
there is no editor for the containing control view. This is nice and fine,
when the text field cell is the only cell of a text field, but in the matrix
and table view case this stops all the cells in the controller from drawing
themselves while there is an editor.

How to get of this trap? We could check if the cell is the selected cell of
its control view and only then not draw it in the editing case. This may
work as a table view has no clear notion of a selected cell and so all cells
will still get drawn, whereas matrix and normal control handle this
correctly.

Another possibility is to move the don't draw check into the control view.
This looks better to me. A cell should always draw itself when asked to do
so, the decision should be put somewhere else.



that seems alright to me, and appears to be what drawRow:clipRect: in
NSTableView is already doing. i've looked at the bug report that code
was added for but didn't have any luck reproducing it with the fix
disabled...



OK, so I submitted this second patch.

Fred


___
Gnustep-dev mailing list
Gnustep-dev@gnu.org
http://lists.gnu.org/mailman/listinfo/gnustep-dev


NSTableView editing problem [Was: Next stable release?]

2008-06-08 Thread Fred Kiefer

Matt Rice wrote:

On Fri, Jun 6, 2008 at 12:32 PM, Fred Kiefer [EMAIL PROTECTED] wrote:

Matt Rice wrote:

I did notice an NSTableView bug though, and its reproducable afaict
with any editable tableview if you edit a field after editing its row
never set as needing display, you have to click a row to get things to
redraw.


Matt,

I did not quite understand this description (Did you mean cell where you
wrote row?), but if you have a fix for this, it surely is welcome.



no, i meant if you double click a cell, then type something and hit
enter or tab keys

after that the whole row is not redrawn (except for the field editor)
and sometimes the whole tableview is blanked out the behaviour changes
on different apps.

I think we can kind of rule out NSTableView I tested the last known
version that I know worked

(r24478 of -make,base,gui,back) and that worked still...

then i tested the svn head versions of make,base,gui,back
with the r24478 version of NSTableView and that produced the same results.



Thank you Matt that is a very interesting finding. I have spend quite 
some time now to test this problme, but failed to get down to the bottom 
of it. It would be best if you put it into our bug system, together with 
the test application you send me off line and all the findings you have 
up to now.


I only tested with the current version of the NSTableView code, but I 
agree, what I see there looks right. But then where does the wrong 
result come from?



NSTableView drawing right now is fairly susceptible to attacks by
things setting it as needing display besides itself.

see NSTableView.m (-drawRect:)

it blanks out the background of the entire rect
with

[self drawBackgroundInClipRect:aRect];
and highlights the selection then draws the grid.

but if you look at -drawRow:clipRect:

if (i != _editedColumn || rowIndex != _editedRow)
   {
  does drawing stuff..
   }

this code is fairly old and uncommented what i recall it doing is
not drawing the edited row or column because it doesn't want to draw
over top of the field editor.



This mechanism seems to work well, form the output I get, the right 
cells get redrawn after hitting return. It just doesn't get visible.

Are we missing a flush somewhere?


anyhow from the same version of NSTableView both working and not
working it seems as though NSTableView doesn't set the edited row rect
as needing display but either the field editor, or NSTextFieldCell or
something else maybe is setting it as needing display that is my
guess... anyways



When finishing editing, the NSTableView sets the edited cell as needing 
display. Then the selection changes and both the old and the new 
selected rows get marked for needing display. All of this is correct.


I even tried to hack into the NSView drawing mechanism and now get a 
report whenever drawRect: gets called and this also seems to be totally 
correct. Here is what I get after finishing editing cell 5/0 of your 
test application:


2008-06-08 18:47:05.419 foo[7021] Drawing view NSTableView: 0x83a0de0 
rect {x = 0; y = 80; width = 481; height = 32}
2008-06-08 18:47:05.420 foo[7021] Draw cell at row 5 col 0 in rect {x = 
4.5; y = 81; width = 91; height = 14}
2008-06-08 18:47:05.420 foo[7021] Draw cell at row 5 col 1 in rect {x = 
104.5; y = 81; width = 372; height = 14}
2008-06-08 18:47:05.420 foo[7021] Draw cell at row 6 col 1 in rect {x = 
104.5; y = 97; width = 372; height = 14}
2008-06-08 18:47:05.420 foo[7021] Draw cell at row 7 col 0 in rect {x = 
4.5; y = 113; width = 91; height = 14}
2008-06-08 18:47:05.420 foo[7021] Draw cell at row 7 col 1 in rect {x = 
104.5; y = 113; width = 372; height = 14}
2008-06-08 18:47:05.420 foo[7021] Drawing view NSClipView: 0x8285be8 
rect {x = 0; y = 0; width = 91; height = 14}
2008-06-08 18:47:05.420 foo[7021] Drawing view NSTextView: 0x82ebe78 
rect {x = 0; y = 0; width = 91; height = 14}



OK, there is no reason to redraw row 7, but this wont do any harm. But 
all the rest is completely as expected. I will now look into the window 
flushing, if this is also correct, I am totally clueless.


Fred


___
Gnustep-dev mailing list
Gnustep-dev@gnu.org
http://lists.gnu.org/mailman/listinfo/gnustep-dev


Re: NSTableView editing problem [Was: Next stable release?]

2008-06-08 Thread Matt Rice
On Sun, Jun 8, 2008 at 10:57 AM, Fred Kiefer [EMAIL PROTECTED] wrote:
 I was completely wrong here. The problem is at a totally different place.
 Look at the code in NSTextFieldsCell that Nicola changed a few months ago:


Ahh, yes changing the below fixes it here i was confused because it is
asked to redraw the edited cell frame, but in the case that it is, the
code is doing what it should by not redrawing.


 - (void) drawInteriorWithFrame: (NSRect)cellFrame inView:
 (NSView*)controlView
 {
  /* Do nothing if there is already a text editor doing the drawing;
   * otherwise, we draw everything twice.  That is bad if there are
   * any transparency involved (eg, even an anti-alias font!) because
   * if the semi-transparent pixels are drawn over themselves they
   * become less transparent (eg, an anti-alias font becomes darker
   * and gives the impression of being bold).
   */
  if (([controlView respondsToSelector: @selector(currentEditor)] == NO)
  || ([(NSTextField *)controlView currentEditor] == nil))
{
  if (_textfieldcell_draws_background)
{
  if ([self isEnabled])
{
  [_background_color set];
}
  else
{
  [[NSColor controlBackgroundColor] set];
}
  NSRectFill([self drawingRectForBounds: cellFrame]);
}

  [super drawInteriorWithFrame: cellFrame inView: controlView];
}
 }

 This basically means that a text field cell will only draw itself, when
 there is no editor for the containing control view. This is nice and fine,
 when the text field cell is the only cell of a text field, but in the matrix
 and table view case this stops all the cells in the controller from drawing
 themselves while there is an editor.

 How to get of this trap? We could check if the cell is the selected cell of
 its control view and only then not draw it in the editing case. This may
 work as a table view has no clear notion of a selected cell and so all cells
 will still get drawn, whereas matrix and normal control handle this
 correctly.

 Another possibility is to move the don't draw check into the control view.
 This looks better to me. A cell should always draw itself when asked to do
 so, the decision should be put somewhere else.


that seems alright to me, and appears to be what drawRow:clipRect: in
NSTableView is already doing. i've looked at the bug report that code
was added for but didn't have any luck reproducing it with the fix
disabled...

 Any better ideas out there?


no but thanks for looking into this.


___
Gnustep-dev mailing list
Gnustep-dev@gnu.org
http://lists.gnu.org/mailman/listinfo/gnustep-dev