OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 2005, 2006, 2008, 2009 Apple Inc. All rights reserved. | 2 * Copyright (C) 2005, 2006, 2008, 2009 Apple Inc. All rights reserved. |
3 * | 3 * |
4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
5 * modification, are permitted provided that the following conditions | 5 * modification, are permitted provided that the following conditions |
6 * are met: | 6 * are met: |
7 * 1. Redistributions of source code must retain the above copyright | 7 * 1. Redistributions of source code must retain the above copyright |
8 * notice, this list of conditions and the following disclaimer. | 8 * notice, this list of conditions and the following disclaimer. |
9 * 2. Redistributions in binary form must reproduce the above copyright | 9 * 2. Redistributions in binary form must reproduce the above copyright |
10 * notice, this list of conditions and the following disclaimer in the | 10 * notice, this list of conditions and the following disclaimer in the |
(...skipping 302 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
313 start = end; | 313 start = end; |
314 end = swap; | 314 end = swap; |
315 } | 315 } |
316 | 316 |
317 // Join up any adjacent text nodes. | 317 // Join up any adjacent text nodes. |
318 if (start.deprecatedNode()->isTextNode()) { | 318 if (start.deprecatedNode()->isTextNode()) { |
319 joinChildTextNodes(start.deprecatedNode()->parentNode(), start, end); | 319 joinChildTextNodes(start.deprecatedNode()->parentNode(), start, end); |
320 start = startPosition(); | 320 start = startPosition(); |
321 end = endPosition(); | 321 end = endPosition(); |
322 } | 322 } |
| 323 |
| 324 if (start.isNull() || end.isNull()) |
| 325 return; |
| 326 |
323 if (end.deprecatedNode()->isTextNode() && start.deprecatedNode()->parentNode
() != end.deprecatedNode()->parentNode()) { | 327 if (end.deprecatedNode()->isTextNode() && start.deprecatedNode()->parentNode
() != end.deprecatedNode()->parentNode()) { |
324 joinChildTextNodes(end.deprecatedNode()->parentNode(), start, end); | 328 joinChildTextNodes(end.deprecatedNode()->parentNode(), start, end); |
325 start = startPosition(); | 329 start = startPosition(); |
326 end = endPosition(); | 330 end = endPosition(); |
327 } | 331 } |
328 | 332 |
| 333 if (start.isNull() || end.isNull()) |
| 334 return; |
| 335 |
329 // Split the start text nodes if needed to apply style. | 336 // Split the start text nodes if needed to apply style. |
330 if (isValidCaretPositionInTextNode(start)) { | 337 if (isValidCaretPositionInTextNode(start)) { |
331 splitTextAtStart(start, end); | 338 splitTextAtStart(start, end); |
332 start = startPosition(); | 339 start = startPosition(); |
333 end = endPosition(); | 340 end = endPosition(); |
334 } | 341 } |
335 | 342 |
336 if (isValidCaretPositionInTextNode(end)) { | 343 if (isValidCaretPositionInTextNode(end)) { |
337 splitTextAtEnd(start, end); | 344 splitTextAtEnd(start, end); |
338 start = startPosition(); | 345 start = startPosition(); |
(...skipping 196 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
535 Node* endDummySpanAncestor = 0; | 542 Node* endDummySpanAncestor = 0; |
536 | 543 |
537 // update document layout once before removing styles | 544 // update document layout once before removing styles |
538 // so that we avoid the expense of updating before each and every call | 545 // so that we avoid the expense of updating before each and every call |
539 // to check a computed style | 546 // to check a computed style |
540 document()->updateLayoutIgnorePendingStylesheets(); | 547 document()->updateLayoutIgnorePendingStylesheets(); |
541 | 548 |
542 // adjust to the positions we want to use for applying style | 549 // adjust to the positions we want to use for applying style |
543 Position start = startPosition(); | 550 Position start = startPosition(); |
544 Position end = endPosition(); | 551 Position end = endPosition(); |
| 552 |
| 553 if (start.isNull() || end.isNull()) |
| 554 return; |
| 555 |
545 if (comparePositions(end, start) < 0) { | 556 if (comparePositions(end, start) < 0) { |
546 Position swap = start; | 557 Position swap = start; |
547 start = end; | 558 start = end; |
548 end = swap; | 559 end = swap; |
549 } | 560 } |
550 | 561 |
551 // split the start node and containing element if the selection starts insid
e of it | 562 // split the start node and containing element if the selection starts insid
e of it |
552 bool splitStart = isValidCaretPositionInTextNode(start); | 563 bool splitStart = isValidCaretPositionInTextNode(start); |
553 if (splitStart) { | 564 if (splitStart) { |
554 if (shouldSplitTextElement(start.deprecatedNode()->parentElement(), styl
e)) | 565 if (shouldSplitTextElement(start.deprecatedNode()->parentElement(), styl
e)) |
(...skipping 865 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1420 } | 1431 } |
1421 | 1432 |
1422 void ApplyStyleCommand::joinChildTextNodes(Node* node, const Position& start, co
nst Position& end) | 1433 void ApplyStyleCommand::joinChildTextNodes(Node* node, const Position& start, co
nst Position& end) |
1423 { | 1434 { |
1424 if (!node) | 1435 if (!node) |
1425 return; | 1436 return; |
1426 | 1437 |
1427 Position newStart = start; | 1438 Position newStart = start; |
1428 Position newEnd = end; | 1439 Position newEnd = end; |
1429 | 1440 |
1430 Node* child = node->firstChild(); | 1441 Vector<RefPtr<Text> > textNodes; |
1431 while (child) { | 1442 for (Node* curr = node->firstChild(); curr; curr = curr->nextSibling()) { |
1432 Node* next = child->nextSibling(); | 1443 if (!curr->isTextNode()) |
1433 if (child->isTextNode() && next && next->isTextNode()) { | 1444 continue; |
1434 Text* childText = toText(child); | 1445 |
1435 Text* nextText = toText(next); | 1446 textNodes.append(toText(curr)); |
1436 if (start.anchorType() == Position::PositionIsOffsetInAnchor && next
== start.containerNode()) | 1447 } |
1437 newStart = Position(childText, childText->length() + start.offse
tInContainerNode()); | 1448 |
1438 if (end.anchorType() == Position::PositionIsOffsetInAnchor && next =
= end.containerNode()) | 1449 for (size_t i = 0; i < textNodes.size(); ++i) { |
1439 newEnd = Position(childText, childText->length() + end.offsetInC
ontainerNode()); | 1450 Text* childText = textNodes[i].get(); |
1440 String textToMove = nextText->data(); | 1451 Node* next = childText->nextSibling(); |
1441 insertTextIntoNode(childText, childText->length(), textToMove); | 1452 if (!next || !next->isTextNode()) |
1442 removeNode(next); | 1453 continue; |
1443 // don't move child node pointer. it may want to merge with more tex
t nodes. | 1454 |
1444 } | 1455 Text* nextText = toText(next); |
1445 else { | 1456 if (start.anchorType() == Position::PositionIsOffsetInAnchor && next ==
start.containerNode()) |
1446 child = child->nextSibling(); | 1457 newStart = Position(childText, childText->length() + start.offsetInC
ontainerNode()); |
1447 } | 1458 if (end.anchorType() == Position::PositionIsOffsetInAnchor && next == en
d.containerNode()) |
| 1459 newEnd = Position(childText, childText->length() + end.offsetInConta
inerNode()); |
| 1460 String textToMove = nextText->data(); |
| 1461 insertTextIntoNode(childText, childText->length(), textToMove); |
| 1462 removeNode(next); |
| 1463 // don't move child node pointer. it may want to merge with more text no
des. |
1448 } | 1464 } |
1449 | 1465 |
1450 updateStartEnd(newStart, newEnd); | 1466 updateStartEnd(newStart, newEnd); |
1451 } | 1467 } |
1452 | 1468 |
1453 } | 1469 } |
OLD | NEW |