Closed
Bug 363839
Opened 19 years ago
Closed 19 years ago
Implement all of SVGPathSegList
Categories
(Core :: SVG, defect)
Tracking
()
RESOLVED
FIXED
People
(Reporter: codedread, Assigned: codedread)
References
Details
Attachments
(4 files, 7 obsolete files)
|
2.36 KB,
image/svg+xml
|
Details | |
|
772 bytes,
image/svg+xml
|
Details | |
|
10.01 KB,
patch
|
jwatt
:
review+
|
Details | Diff | Splinter Review |
|
10.00 KB,
patch
|
tor
:
superreview+
|
Details | Diff | Splinter Review |
User-Agent: Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.8.1) Gecko/20061023 SUSE/2.0-30 Firefox/2.0
Build Identifier: Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.8.1) Gecko/20061023 SUSE/2.0-30 Firefox/2.0
SVGPathSegList has two major implementation issues:
1) SVGPathSegList does not implement insertItemBefore() and replaceItem()
2) As per spec http://www.w3.org/TR/SVG11/paths.html#InterfaceSVGPathSegList, appendItem() is supposed to remove a SVGPathSeg if it is already part of another list.
I have test cases and a patch for these once Bug 363086 is fixed.
Reproducible: Always
Steps to Reproduce:
1. Run test cases
2.
3.
Actual Results:
Green squares do not result in Firefox 2 or in the Firefox trunk.
Expected Results:
Test cases should produce green squares.
| Assignee | ||
Comment 1•19 years ago
|
||
| Assignee | ||
Comment 2•19 years ago
|
||
Comment 3•19 years ago
|
||
duplicate of bug 254712?
| Assignee | ||
Comment 4•19 years ago
|
||
Seems you are right, though Bug 254712 appears to be broader than SVGPathSegList (Bug 254712 depends on Bug 282247, which says all Lists should have a base class).
I agree with these other two bugs, but it means my pending patch needs to be rewritten - or we can accept my patch for just SVGPathSegList and I will get working on Bugs 282247 and 254712.
I will leave it to tor/jwatt/roc to decide, since I'm new to this.
| Assignee | ||
Comment 5•19 years ago
|
||
Also includes fix for Bug 363086. See my comment #4 regarding this patch.
Attachment #248826 -
Flags: review?(tor)
Comment on attachment 248826 [details] [diff] [review]
Patch (see Comment #4)
>+nsCOMPtr<nsISVGValue>
>+nsSVGPathSeg::GetParent() const
>+{
>+ return do_QueryReferent(mParent);
>+}
nsCOMPtr shouldn't be used as a return value - see "nsCOMPtrs in function signatures" in http://www.mozilla.org/projects/xpcom/nsCOMPtr.html .
> /* nsIDOMSVGPathSeg insertItemBefore (in nsIDOMSVGPathSeg newItem, in unsigned long index); */
> NS_IMETHODIMP nsSVGPathSegList::InsertItemBefore(nsIDOMSVGPathSeg *newItem,
> PRUint32 index,
> nsIDOMSVGPathSeg **_retval)
> {
...
>+ // The SVG specs state that 'if newItem is already in a list, it
>+ // is removed from its previous list before it is inserted into this
>+ // list'.
>+ nsSVGPathSeg *newSeg = NS_STATIC_CAST(nsSVGPathSeg*, newItem);
>+ if(newSeg && newSeg->GetParent()) {
mozilla code style - space after "if".
>+ // newItem's parent must be cast back to a nsSVGPathSegList*
>+ nsSVGPathSegList* oldSegList = NS_STATIC_CAST(nsSVGPathSegList*, newSeg->GetParent().get());
>+ if(oldSegList) {
>+ PRInt32 ix = oldSegList->mSegments.IndexOfObject(newSeg);
>+ if(ix != -1) { oldSegList->RemoveElementAt(ix); }
ditto, plus blocks start a new line.
>+ }
>+ }
This new code that you duplicate a number of times should be turned into a helper function/method.
Attachment #248826 -
Flags: review?(tor) → review-
| Assignee | ||
Comment 7•19 years ago
|
||
New helper method added to avoid code duplication. nsQueryReferent now returned from nsSVGPathSeg::GetParent(), I hope this is correct...
Attachment #248826 -
Attachment is obsolete: true
Attachment #250547 -
Flags: review?(tor)
| Assignee | ||
Comment 8•19 years ago
|
||
woops - last patch had some cruft in it...
Attachment #250547 -
Attachment is obsolete: true
Attachment #250548 -
Flags: review?
Attachment #250547 -
Flags: review?(tor)
| Assignee | ||
Updated•19 years ago
|
Attachment #250548 -
Flags: review? → review?(tor)
| Assignee | ||
Comment 9•19 years ago
|
||
Woops - somehow I missed fixing the coding convention comment.
Attachment #250548 -
Attachment is obsolete: true
Attachment #250675 -
Flags: review?(tor)
Attachment #250548 -
Flags: review?(tor)
| Assignee | ||
Comment 10•19 years ago
|
||
Argh - I swear I'll get better at this... I need a better system to manage patches ;)
Attachment #250675 -
Attachment is obsolete: true
Attachment #250677 -
Flags: review?(tor)
Attachment #250675 -
Flags: review?(tor)
Comment 11•19 years ago
|
||
Comment on attachment 250677 [details] [diff] [review]
Fixed patch file typo
>+void
>+nsSVGPathSegList::EnsureElementIsParentless(nsIDOMSVGPathSeg* aSeg)
>+{
>+ nsSVGPathSeg *theSeg = NS_STATIC_CAST(nsSVGPathSeg*, aSeg);
>+ nsCOMPtr<nsISVGValue> theParent = theSeg->GetParent();
>+ if (theSeg && theParent) {
>+ // newItem's parent must be cast back to a nsSVGPathSegList*
>+ nsSVGPathSegList* otherSegList = NS_STATIC_CAST(nsSVGPathSegList*, theParent.get());
>+ if (otherSegList) {
If theParent is non-null (already checked), so will this. Remove the extra test.
With that, r=tor.
Attachment #250677 -
Flags: review?(tor) → review+
| Assignee | ||
Comment 12•19 years ago
|
||
Fixed per tor's comment. However, I uncovered a bug in the proposed InsertItemBefore implementation:
Per the SVG spec, if InsertItemBefore is called with an out-of-range index, then the item is appended. I borrowed the implementation from nsSVGNumberList.
Can you re-review? Does it also need a super-review?
Attachment #250677 -
Attachment is obsolete: true
Attachment #251236 -
Flags: review?(tor)
Comment 13•19 years ago
|
||
Comment on attachment 251236 [details] [diff] [review]
Updated patch per tor's comments
>+nsCOMPtr<nsISVGValue>
>+nsSVGPathSeg::GetParent() const
>+{
>+ return do_QueryReferent(mParent);
>+}
Somehow you seem to have changed the return type to nsCOMPtr, so your code won't compile.
Not something you have to do because since it wasn't you who named it, but it would be nice if this was GetOwnerList and mOwnerList. That seems like more accurate naming to me, and besides we have enough GetParent functions that it's already hard enough to search for the code you're interested in.
> NS_IMETHODIMP nsSVGPathSegList::InsertItemBefore(nsIDOMSVGPathSeg *newItem,
> PRUint32 index,
> nsIDOMSVGPathSeg **_retval)
> {
>- // null check when implementing - this method can be used by scripts!
>- // if (!newItem)
>- // return NS_ERROR_DOM_SVG_WRONG_TYPE_ERR;
>+ *_retval = newItem;
>+ if (!newItem)
>+ return NS_ERROR_DOM_SVG_WRONG_TYPE_ERR;
>
>- NS_NOTYETIMPLEMENTED("nsSVGPathSegList::InsertItemBefore");
>- return NS_ERROR_NOT_IMPLEMENTED;
>+ EnsureElementIsParentless(newItem);
In my opinion we should not remove the item from its current list unless we successfully add it to this one. Therefore EnsureElementIsParentless should be called last. Actually I think you would be better to only call EnsureElementIsParentless in AppendElement and InsertElementAt (at the end of those methods of course). Then you only need two calls instead of three.
>+ PRInt32 idx = index;
>+ PRInt32 count = mElements.Count();
>+ if (!InsertElementAt(newItem, (idx < count)? idx: count)) {
This is a good idea, but again it won't compile because nsSVGPathSegList::InsertElementAt has void as its return value. I'd suggest just leaving as it was in your previous patch for now. When all List implementations get merged into a base class then they should pick up the improvements in nsSVGTransformList which does check for this type of failure. For now just keep it simple.
>+nsSVGPathSegList::EnsureElementIsParentless(nsIDOMSVGPathSeg* aSeg)
>+{
>+ nsSVGPathSeg *theSeg = NS_STATIC_CAST(nsSVGPathSeg*, aSeg);
>+ nsCOMPtr<nsISVGValue> theParent = theSeg->GetParent();
>+ if (theSeg && theParent) {
>+ // newItem's parent must be cast back to a nsSVGPathSegList*
>+ nsSVGPathSegList* otherSegList = NS_STATIC_CAST(nsSVGPathSegList*, theParent.get());
>+ PRInt32 ix = otherSegList->mSegments.IndexOfObject(theSeg);
>+ if (ix != -1) { otherSegList->RemoveElementAt(ix); }
Please spread that back over three lines as it was.
r- since this won't compile. Please be sure to check your patches compile and are tested before putting them up for review.
Attachment #251236 -
Flags: review?(tor) → review-
| Assignee | ||
Comment 14•19 years ago
|
||
Thanks, Jonathan. I agree with your first two suggestions 1) renaming GetParent, SetParent and 2) fixing GetParent() again, which I accidentally regressed from my earlier patch.
Also, sorry about not testing the patch first - you're right, InsertElementAt() would need to be modified for its return type. I agree that I will do this with the base List class later.
And again, for the coding convention, I apologize for regressing that yet again. I need a better system of managing my patches, clearly.
As for calling EnsureElementIsParentless() - we can't call that afterwards, because it removes the element from its current list (which is what AppendItem does). I'll have to figure out a better solution (I guess save the old parent and then remove it from the old list after we've successfully added it to the new list).
| Assignee | ||
Comment 15•19 years ago
|
||
Attachment #251236 -
Attachment is obsolete: true
Attachment #251287 -
Flags: review?(jwatt)
| Assignee | ||
Comment 16•19 years ago
|
||
Btw, i took your suggestion and moved EnsureElementIsParentless() into the append/insert helper functions as you suggested. This somewhat solved my dilemma since by the time we get to the helper functions we're definitely doing the add/insert (there are no error scenarios there). I still do it first though within those helper functions.
Comment 17•19 years ago
|
||
Comment on attachment 251287 [details] [diff] [review]
Implemented all of jwatt's comments
+nsSVGPathSeg::SetOwnerList(nsISVGValue* aParent)
aParent -> aOwnerList
>+ nsresult SetOwnerList(nsISVGValue* aParent);
same
>+ void EnsureElementIsParentless(nsIDOMSVGPathSeg*);
Again, the word "parent" is in the name. Maybe this should be called RemoveFromCurrentList? Hmm, and then SetOwnerList should be named SetCurrentList. :-/ Actually I do like that better if you don't mind doing it. Note that would change my comments above of course.
>+ EnsureElementIsParentless(aElement);
Can you put a comment before these two calls along the lines of:
// XXX: we should only remove an item from its current list if we
// successfully added it to this list
>+nsSVGPathSegList::EnsureElementIsParentless(nsIDOMSVGPathSeg* aSeg)
>+{
>+ nsSVGPathSeg *theSeg = NS_STATIC_CAST(nsSVGPathSeg*, aSeg);
>+ nsCOMPtr<nsISVGValue> theParent = theSeg->GetOwnerList();
>+ if (theSeg && theParent) {
Checking theSeg is redundant.
| Assignee | ||
Comment 18•19 years ago
|
||
Attachment #251287 -
Attachment is obsolete: true
Attachment #251287 -
Flags: review?(jwatt)
| Assignee | ||
Updated•19 years ago
|
Attachment #251294 -
Flags: review?(jwatt)
Comment 19•19 years ago
|
||
Comment on attachment 251294 [details] [diff] [review]
Updated for jwatt's suggested naming
>+ nsSVGPathSeg() : mCurrentList(nsnull) {}
>+ nsresult SetCurrentList(nsISVGValue* aParent);
aCurrentList
>+nsSVGPathSegList::RemoveFromCurrentList(nsIDOMSVGPathSeg* aSeg)
>+{
>+ nsSVGPathSeg *theSeg = NS_STATIC_CAST(nsSVGPathSeg*, aSeg);
>+ nsCOMPtr<nsISVGValue> theParent = theSeg->GetCurrentList();
>+ if (theParent) {
currentList please. Bet that's the last time you listen to me about better naming. ;-)
r=jwatt. Nice. Thanks Jeff!
Attachment #251294 -
Flags: review?(jwatt) → review+
| Assignee | ||
Comment 20•19 years ago
|
||
Ugh, I was going to do a text search for "parent" too - looks like I should have, sorry. Can't re-submit the patch until tonight now though.
| Assignee | ||
Comment 21•19 years ago
|
||
Attachment #251322 -
Flags: superreview?(tor)
Updated•19 years ago
|
Assignee: general → codedread
Status: UNCONFIRMED → NEW
Ever confirmed: true
Attachment #251322 -
Flags: superreview?(tor) → superreview+
Comment 22•19 years ago
|
||
Checked in for Jeff.
Status: NEW → RESOLVED
Closed: 19 years ago
Resolution: --- → FIXED
You need to log in
before you can comment on or make changes to this bug.
Description
•