Bug 43639

Summary: Undo fails in RemoveCSSPropertyCommand when the corresponding style attribute is removed
Product: WebKit Reporter: Ryosuke Niwa <rniwa>
Component: HTML EditingAssignee: Ryosuke Niwa <rniwa>
Status: RESOLVED FIXED    
Severity: Normal CC: darin, eric, jparent, justin.garcia, ojan, tony
Priority: P2    
Version: 528+ (Nightly build)   
Hardware: All   
OS: All   
Bug Depends on:    
Bug Blocks: 26871    
Attachments:
Description Flags
demonstrates the bug
none
fixes the bug
none
Added more tests
none
modified RemoveCSSPropertyCommand to restore styled element instead of style justin.garcia: review+

Ryosuke Niwa
Reported 2010-08-06 13:37:46 PDT
Created attachment 63755 [details] demonstrates the bug Currently, the only usage of RemoveCSSPropertyCommand to trim some CSS property from a given HTML element. However, because it only modifies CSSMutableStyleDeclaration and not the attribute of the styled element, RemoveCSSPropertyCommand cannot undo the removal if the style attribute of the corresponding element gets removed afterwards. This happens when a CSS style is removed and style attribute becomes empty. To fix this problem, we should re-implement removeCSSProperty using setNodeAttribute.
Attachments
demonstrates the bug (238 bytes, text/html)
2010-08-06 13:37 PDT, Ryosuke Niwa
no flags
fixes the bug (26.56 KB, patch)
2010-08-06 14:47 PDT, Ryosuke Niwa
no flags
Added more tests (28.55 KB, patch)
2010-08-06 15:17 PDT, Ryosuke Niwa
no flags
modified RemoveCSSPropertyCommand to restore styled element instead of style (15.66 KB, patch)
2010-08-09 15:31 PDT, Ryosuke Niwa
justin.garcia: review+
Ryosuke Niwa
Comment 1 2010-08-06 14:47:26 PDT
Created attachment 63763 [details] fixes the bug
Ryosuke Niwa
Comment 2 2010-08-06 14:48:25 PDT
The patch is large because I had to delete RemoveCSSPropertyCommand.h/.cpp from all build files but the code change itself is trivial and must be easy to review.
Ryosuke Niwa
Comment 3 2010-08-06 14:57:34 PDT
Comment on attachment 63763 [details] fixes the bug Need to add one more test.
Ryosuke Niwa
Comment 4 2010-08-06 15:17:12 PDT
Created attachment 63769 [details] Added more tests
Justin Garcia
Comment 5 2010-08-09 11:25:22 PDT
> Currently, the only usage of RemoveCSSPropertyCommand to trim some CSS property from a given HTML element. However, because it only modifies CSSMutableStyleDeclaration and not the attribute of the styled element, RemoveCSSPropertyCommand cannot undo the removal if the style attribute of the corresponding element gets removed afterwards. This happens when a CSS style is removed and style attribute becomes empty. The new approach has a higher memory overhead, since we hold on to the entire style string just to remove one property. Can we just give RemoveCSSPropertyCommand the ability to remove the style attribute if removing the property empties the inline style declaration? And I can't see where the new implementation removes the style attribute when necessary like you say: -void CompositeEditCommand::removeCSSProperty(PassRefPtr<CSSMutableStyleDeclaration> style, CSSPropertyID property) +void CompositeEditCommand::removeCSSProperty(PassRefPtr<StyledElement> element, CSSPropertyID property) { - applyCommandToComposite(RemoveCSSPropertyCommand::create(document(), style, property)); + RefPtr<CSSMutableStyleDeclaration> style = element->inlineStyleDecl(); + if (!style->getPropertyCSSValue(property)) + return; + style = style->copy(); + style->removeProperty(property); + setNodeAttribute(element, styleAttr, style->cssText()); }
Justin Garcia
Comment 6 2010-08-09 11:27:15 PDT
> And I can't see where the new implementation removes the style attribute when necessary like you say: Oops, looks like Element::setAttribute does it.
Ryosuke Niwa
Comment 7 2010-08-09 12:22:45 PDT
(In reply to comment #5) > The new approach has a higher memory overhead, since we hold on to the entire style string just to remove one property. Can we just give RemoveCSSPropertyCommand the ability to remove the style attribute if removing the property empties the inline style declaration? Right, it's a higher overhead but I don't think removing the style attribute within RemoveCSSPropertyCommand solves the problem because there are other places (applyRelativeFontStyleChange, applyInlineStyleToRange, & applyTextDecorationStyle in ApplyStyleCommand for example) where we generate style attribute as a string and use setNodeAttribute to update, resulting in the loss of CSSMutableStyleDeclaration. We could remember the property we removed though. > And I can't see where the new implementation removes the style attribute when necessary like you say: My point isn't really to remove the attribute inside of removeCSSProperty. removeCSSProperty is used in ApplyStyleCommand to remove text decoration and such and we manually remove the attribute whenever style attribute is empty (see applyRelativeFontStyleChange, removeEmbeddingUpToEnclosingBlock, removeHTMLBidiEmbeddingStyle, removeCSSStyle for instance).
Ryosuke Niwa
Comment 8 2010-08-09 15:31:35 PDT
Created attachment 63942 [details] modified RemoveCSSPropertyCommand to restore styled element instead of style
Justin Garcia
Comment 9 2010-08-09 16:07:59 PDT
Comment on attachment 63942 [details] modified RemoveCSSPropertyCommand to restore styled element instead of style r=me
Ryosuke Niwa
Comment 10 2010-08-09 16:21:04 PDT
(In reply to comment #9) > (From update of attachment 63942 [details]) > r=me Thanks for the promptly review!
Ryosuke Niwa
Comment 11 2010-08-09 16:25:28 PDT
Note You need to log in before you can comment on or make changes to this bug.