Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(208)

Side by Side Diff: chrome/browser/resources/chromeos/chromevox/cvox2/background/cursors.js

Issue 2943193002: Run clang-format on .js files in c/b/r/chromeos/chromevox (Closed)
Patch Set: Created 3 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 /** 5 /**
6 * @fileoverview Classes related to cursors that point to and select parts of 6 * @fileoverview Classes related to cursors that point to and select parts of
7 * the automation tree. 7 * the automation tree.
8 */ 8 */
9 9
10 goog.provide('cursors.Cursor'); 10 goog.provide('cursors.Cursor');
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after
81 // Re-interpret this case as the beginning of the next node. 81 // Re-interpret this case as the beginning of the next node.
82 var nextNode = AutomationUtil.findNextNode( 82 var nextNode = AutomationUtil.findNextNode(
83 node, Dir.FORWARD, AutomationPredicate.leafOrStaticText); 83 node, Dir.FORWARD, AutomationPredicate.leafOrStaticText);
84 84
85 // The exception is when a user types at the end of a line. In that case, 85 // The exception is when a user types at the end of a line. In that case,
86 // staying on the current node is appropriate. 86 // staying on the current node is appropriate.
87 if (node && node.nextOnLine && nextNode) { 87 if (node && node.nextOnLine && nextNode) {
88 node = nextNode; 88 node = nextNode;
89 index = 0; 89 index = 0;
90 } 90 }
91 } else if (node.role == RoleType.GENERIC_CONTAINER && 91 } else if (
92 node.state.richlyEditable && 92 node.role == RoleType.GENERIC_CONTAINER && node.state.richlyEditable &&
93 (node.firstChild && (node.firstChild.role == RoleType.LINE_BREAK || 93 (node.firstChild &&
94 node.firstChild.role == RoleType.STATIC_TEXT))) { 94 (node.firstChild.role == RoleType.LINE_BREAK ||
95 node.firstChild.role == RoleType.STATIC_TEXT))) {
95 // Re-interpret this case as pointing to the text under the div. 96 // Re-interpret this case as pointing to the text under the div.
96 node = node.find({ role: RoleType.INLINE_TEXT_BOX }) || node; 97 node = node.find({role: RoleType.INLINE_TEXT_BOX}) || node;
97 } 98 }
98 99
99 /** @type {number} @private */ 100 /** @type {number} @private */
100 this.index_ = index; 101 this.index_ = index;
101 /** @type {Array<AutomationNode>} @private */ 102 /** @type {Array<AutomationNode>} @private */
102 this.ancestry_ = []; 103 this.ancestry_ = [];
103 var nodeWalker = node; 104 var nodeWalker = node;
104 while (nodeWalker) { 105 while (nodeWalker) {
105 this.ancestry_.push(nodeWalker); 106 this.ancestry_.push(nodeWalker);
106 nodeWalker = nodeWalker.parent; 107 nodeWalker = nodeWalker.parent;
(...skipping 12 matching lines...) Expand all
119 }; 120 };
120 121
121 cursors.Cursor.prototype = { 122 cursors.Cursor.prototype = {
122 /** 123 /**
123 * Returns true if |rhs| is equal to this cursor. 124 * Returns true if |rhs| is equal to this cursor.
124 * Use this for strict equality between cursors. 125 * Use this for strict equality between cursors.
125 * @param {!cursors.Cursor} rhs 126 * @param {!cursors.Cursor} rhs
126 * @return {boolean} 127 * @return {boolean}
127 */ 128 */
128 equals: function(rhs) { 129 equals: function(rhs) {
129 return this.node === rhs.node && 130 return this.node === rhs.node && this.index === rhs.index;
130 this.index === rhs.index;
131 }, 131 },
132 132
133 /** 133 /**
134 * Returns true if |rhs| is equal to this cursor. 134 * Returns true if |rhs| is equal to this cursor.
135 * Use this for loose equality between cursors where specific character-based 135 * Use this for loose equality between cursors where specific character-based
136 * indicies do not matter such as when processing node-targeted events. 136 * indicies do not matter such as when processing node-targeted events.
137 * @param {!cursors.Cursor} rhs 137 * @param {!cursors.Cursor} rhs
138 * @return {boolean} 138 * @return {boolean}
139 */ 139 */
140 contentEquals: function(rhs) { 140 contentEquals: function(rhs) {
141 // First, normalize the two nodes so they both point to the first non-text 141 // First, normalize the two nodes so they both point to the first non-text
142 // node. 142 // node.
143 var lNode = this.node; 143 var lNode = this.node;
144 var rNode = rhs.node; 144 var rNode = rhs.node;
145 while (lNode && (lNode.role == RoleType.INLINE_TEXT_BOX || 145 while (lNode &&
146 lNode.role == RoleType.STATIC_TEXT)) 146 (lNode.role == RoleType.INLINE_TEXT_BOX ||
147 lNode.role == RoleType.STATIC_TEXT))
147 lNode = lNode.parent; 148 lNode = lNode.parent;
148 while (rNode && (rNode.role == RoleType.INLINE_TEXT_BOX || 149 while (rNode &&
149 rNode.role == RoleType.STATIC_TEXT)) 150 (rNode.role == RoleType.INLINE_TEXT_BOX ||
151 rNode.role == RoleType.STATIC_TEXT))
150 rNode = rNode.parent; 152 rNode = rNode.parent;
151 153
152 // Ignore indicies for now. 154 // Ignore indicies for now.
153 155
154 return lNode === rNode && lNode != undefined; 156 return lNode === rNode && lNode != undefined;
155 }, 157 },
156 158
157 /** 159 /**
158 * Compares this cursor with |rhs|. 160 * Compares this cursor with |rhs|.
159 * @param {cursors.Cursor} rhs 161 * @param {cursors.Cursor} rhs
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after
209 if (adjustedNode.state.editable) 211 if (adjustedNode.state.editable)
210 return adjustedNode; 212 return adjustedNode;
211 213
212 // Selections over line break nodes are broken. 214 // Selections over line break nodes are broken.
213 var parent = adjustedNode.parent; 215 var parent = adjustedNode.parent;
214 var grandparent = parent && parent.parent; 216 var grandparent = parent && parent.parent;
215 if (parent && parent.role == RoleType.LINE_BREAK) { 217 if (parent && parent.role == RoleType.LINE_BREAK) {
216 adjustedNode = grandparent; 218 adjustedNode = grandparent;
217 } else if (grandparent && grandparent.role == RoleType.LINE_BREAK) { 219 } else if (grandparent && grandparent.role == RoleType.LINE_BREAK) {
218 adjustedNode = grandparent.parent; 220 adjustedNode = grandparent.parent;
219 } else if (this.index_ == cursors.NODE_INDEX || 221 } else if (
222 this.index_ == cursors.NODE_INDEX ||
220 adjustedNode.role == RoleType.INLINE_TEXT_BOX || 223 adjustedNode.role == RoleType.INLINE_TEXT_BOX ||
221 adjustedNode.nameFrom != chrome.automation.NameFromType.CONTENTS) { 224 adjustedNode.nameFrom != chrome.automation.NameFromType.CONTENTS) {
222 // A node offset or unselectable character offset. 225 // A node offset or unselectable character offset.
223 adjustedNode = parent; 226 adjustedNode = parent;
224 } else { 227 } else {
225 // A character offset into content. 228 // A character offset into content.
226 adjustedNode = 229 adjustedNode =
227 adjustedNode.find({role: RoleType.STATIC_TEXT}) || adjustedNode; 230 adjustedNode.find({role: RoleType.STATIC_TEXT}) || adjustedNode;
228 } 231 }
229 232
230 return adjustedNode || null; 233 return adjustedNode || null;
231 }, 234 },
232 235
233 /** 236 /**
234 * An index appropriate for making selections. If this cursor has a 237 * An index appropriate for making selections. If this cursor has a
235 * cursors.NODE_INDEX index, the selection index is a node offset e.g. the 238 * cursors.NODE_INDEX index, the selection index is a node offset e.g. the
236 * index in parent. If not, the index is a character offset. 239 * index in parent. If not, the index is a character offset.
237 * @return {number} 240 * @return {number}
238 * @private 241 * @private
239 */ 242 */
240 get selectionIndex_() { 243 get selectionIndex_() {
241 var adjustedIndex = this.index_; 244 var adjustedIndex = this.index_;
242 245
243 if (!this.node) 246 if (!this.node)
244 return -1; 247 return -1;
245 248
246 if (this.node.state.editable) { 249 if (this.node.state.editable) {
247 return this.index_ == cursors.NODE_INDEX ? 0 : this.index_; 250 return this.index_ == cursors.NODE_INDEX ? 0 : this.index_;
248 } else if (this.node.role == RoleType.INLINE_TEXT_BOX && 251 } else if (
249 // Selections under a line break are broken. 252 this.node.role == RoleType.INLINE_TEXT_BOX &&
253 // Selections under a line break are broken.
250 this.node.parent && this.node.parent.role != RoleType.LINE_BREAK) { 254 this.node.parent && this.node.parent.role != RoleType.LINE_BREAK) {
251 if (adjustedIndex == cursors.NODE_INDEX) 255 if (adjustedIndex == cursors.NODE_INDEX)
252 adjustedIndex = 0; 256 adjustedIndex = 0;
253 257
254 var sibling = this.node.previousSibling; 258 var sibling = this.node.previousSibling;
255 while (sibling) { 259 while (sibling) {
256 adjustedIndex += sibling.name.length; 260 adjustedIndex += sibling.name.length;
257 sibling = sibling.previousSibling; 261 sibling = sibling.previousSibling;
258 } 262 }
259 } else if (this.index_ == cursors.NODE_INDEX || 263 } else if (
264 this.index_ == cursors.NODE_INDEX ||
260 this.node.nameFrom != chrome.automation.NameFromType.CONTENTS) { 265 this.node.nameFrom != chrome.automation.NameFromType.CONTENTS) {
261 // A node offset or unselectable character offset. 266 // A node offset or unselectable character offset.
262 267
263 // The selected node could have been adjusted upwards in the tree. 268 // The selected node could have been adjusted upwards in the tree.
264 var childOfSelection = this.node; 269 var childOfSelection = this.node;
265 do { 270 do {
266 adjustedIndex = childOfSelection.indexInParent || 0; 271 adjustedIndex = childOfSelection.indexInParent || 0;
267 childOfSelection = childOfSelection.parent; 272 childOfSelection = childOfSelection.parent;
268 } while (childOfSelection && childOfSelection != this.selectionNode_); 273 } while (childOfSelection && childOfSelection != this.selectionNode_);
269 } 274 }
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
305 // BOUND and DIRECTIONAL are the same for characters. 310 // BOUND and DIRECTIONAL are the same for characters.
306 var text = this.getText(); 311 var text = this.getText();
307 newIndex = dir == Dir.FORWARD ? 312 newIndex = dir == Dir.FORWARD ?
308 StringUtil.nextCodePointOffset(text, newIndex) : 313 StringUtil.nextCodePointOffset(text, newIndex) :
309 StringUtil.previousCodePointOffset(text, newIndex); 314 StringUtil.previousCodePointOffset(text, newIndex);
310 if (newIndex < 0 || newIndex >= text.length) { 315 if (newIndex < 0 || newIndex >= text.length) {
311 newNode = AutomationUtil.findNextNode( 316 newNode = AutomationUtil.findNextNode(
312 newNode, dir, AutomationPredicate.leafWithText); 317 newNode, dir, AutomationPredicate.leafWithText);
313 if (newNode) { 318 if (newNode) {
314 var newText = AutomationUtil.getText(newNode); 319 var newText = AutomationUtil.getText(newNode);
315 newIndex = 320 newIndex = dir == Dir.FORWARD ?
316 dir == Dir.FORWARD ? 0 : 321 0 :
317 StringUtil.previousCodePointOffset(newText, newText.length); 322 StringUtil.previousCodePointOffset(newText, newText.length);
318 newIndex = Math.max(newIndex, 0); 323 newIndex = Math.max(newIndex, 0);
319 } else { 324 } else {
320 newIndex = this.index_; 325 newIndex = this.index_;
321 } 326 }
322 } 327 }
323 break; 328 break;
324 case Unit.WORD: 329 case Unit.WORD:
325 if (newNode.role != RoleType.INLINE_TEXT_BOX) { 330 if (newNode.role != RoleType.INLINE_TEXT_BOX) {
326 newNode = AutomationUtil.findNextNode(newNode, 331 newNode = AutomationUtil.findNextNode(
327 Dir.FORWARD, 332 newNode, Dir.FORWARD, AutomationPredicate.inlineTextBox,
328 AutomationPredicate.inlineTextBox, 333 {skipInitialSubtree: false}) ||
329 {skipInitialSubtree: false}) || newNode; 334 newNode;
330 } 335 }
331 switch (movement) { 336 switch (movement) {
332 case Movement.BOUND: 337 case Movement.BOUND:
333 if (newNode.role == RoleType.INLINE_TEXT_BOX) { 338 if (newNode.role == RoleType.INLINE_TEXT_BOX) {
334 var start, end; 339 var start, end;
335 for (var i = 0; i < newNode.wordStarts.length; i++) { 340 for (var i = 0; i < newNode.wordStarts.length; i++) {
336 if (newIndex >= newNode.wordStarts[i] && 341 if (newIndex >= newNode.wordStarts[i] &&
337 newIndex <= newNode.wordEnds[i]) { 342 newIndex <= newNode.wordEnds[i]) {
338 start = newNode.wordStarts[i]; 343 start = newNode.wordStarts[i];
339 end = newNode.wordEnds[i]; 344 end = newNode.wordEnds[i];
(...skipping 18 matching lines...) Expand all
358 break; 363 break;
359 } 364 }
360 } 365 }
361 if (goog.isDef(start)) { 366 if (goog.isDef(start)) {
362 newIndex = start; 367 newIndex = start;
363 } else { 368 } else {
364 // The backward case is special at the beginning of nodes. 369 // The backward case is special at the beginning of nodes.
365 if (dir == Dir.BACKWARD && newIndex != 0) { 370 if (dir == Dir.BACKWARD && newIndex != 0) {
366 newIndex = 0; 371 newIndex = 0;
367 } else { 372 } else {
368 newNode = AutomationUtil.findNextNode(newNode, dir, 373 newNode = AutomationUtil.findNextNode(
369 AutomationPredicate.leaf); 374 newNode, dir, AutomationPredicate.leaf);
370 if (newNode) { 375 if (newNode) {
371 newIndex = 0; 376 newIndex = 0;
372 if (dir == Dir.BACKWARD && 377 if (dir == Dir.BACKWARD &&
373 newNode.role == RoleType.INLINE_TEXT_BOX) { 378 newNode.role == RoleType.INLINE_TEXT_BOX) {
374 var starts = newNode.wordStarts; 379 var starts = newNode.wordStarts;
375 newIndex = starts[starts.length - 1] || 0; 380 newIndex = starts[starts.length - 1] || 0;
376 } else { 381 } else {
377 // TODO(dtseng): Figure out what to do for general nodes. 382 // TODO(dtseng): Figure out what to do for general nodes.
378 } 383 }
379 } 384 }
380 } 385 }
381 } 386 }
382 } else { 387 } else {
383 // TODO(dtseng): Figure out what to do in this case. 388 // TODO(dtseng): Figure out what to do in this case.
384 } 389 }
385 } 390 }
386 break; 391 break;
387 case Unit.TEXT: 392 case Unit.TEXT:
388 case Unit.NODE: 393 case Unit.NODE:
389 switch (movement) { 394 switch (movement) {
390 case Movement.BOUND: 395 case Movement.BOUND:
391 newIndex = dir == Dir.FORWARD ? this.getText().length - 1 : 0; 396 newIndex = dir == Dir.FORWARD ? this.getText().length - 1 : 0;
392 break; 397 break;
393 case Movement.DIRECTIONAL: 398 case Movement.DIRECTIONAL:
394 var pred = unit == Unit.TEXT ? 399 var pred = unit == Unit.TEXT ? AutomationPredicate.leaf :
395 AutomationPredicate.leaf : AutomationPredicate.object; 400 AutomationPredicate.object;
396 newNode = AutomationUtil.findNextNode(newNode, dir, pred) || 401 newNode =
397 originalNode; 402 AutomationUtil.findNextNode(newNode, dir, pred) || originalNode;
398 newIndex = cursors.NODE_INDEX; 403 newIndex = cursors.NODE_INDEX;
399 break; 404 break;
400 } 405 }
401 break; 406 break;
402 case Unit.LINE: 407 case Unit.LINE:
403 var deepEquivalent = this.deepEquivalent; 408 var deepEquivalent = this.deepEquivalent;
404 newNode = deepEquivalent.node || newNode; 409 newNode = deepEquivalent.node || newNode;
405 newIndex = deepEquivalent.index || 0; 410 newIndex = deepEquivalent.index || 0;
406 411
407 switch (movement) { 412 switch (movement) {
408 case Movement.BOUND: 413 case Movement.BOUND:
409 newNode = AutomationUtil.findNodeUntil(newNode, dir, 414 newNode = AutomationUtil.findNodeUntil(
410 AutomationPredicate.linebreak, true); 415 newNode, dir, AutomationPredicate.linebreak, true);
411 newNode = newNode || originalNode; 416 newNode = newNode || originalNode;
412 newIndex = 417 newIndex =
413 dir == Dir.FORWARD ? AutomationUtil.getText(newNode).length : 0; 418 dir == Dir.FORWARD ? AutomationUtil.getText(newNode).length : 0;
414 break; 419 break;
415 case Movement.DIRECTIONAL: 420 case Movement.DIRECTIONAL:
416 newNode = AutomationUtil.findNodeUntil( 421 newNode = AutomationUtil.findNodeUntil(
417 newNode, dir, AutomationPredicate.linebreak); 422 newNode, dir, AutomationPredicate.linebreak);
418 break; 423 break;
419 } 424 }
420 break; 425 break;
421 default: 426 default:
422 throw Error('Unrecognized unit: ' + unit); 427 throw Error('Unrecognized unit: ' + unit);
423 } 428 }
424 newNode = newNode || originalNode; 429 newNode = newNode || originalNode;
425 newIndex = goog.isDef(newIndex) ? newIndex : this.index_; 430 newIndex = goog.isDef(newIndex) ? newIndex : this.index_;
426 return new cursors.Cursor(newNode, newIndex); 431 return new cursors.Cursor(newNode, newIndex);
427 }, 432 },
428 433
429 /** 434 /**
430 * Returns the deepest equivalent cursor. 435 * Returns the deepest equivalent cursor.
(...skipping 12 matching lines...) Expand all
443 if (length <= newIndex && newIndex < (length + target.name.length)) 448 if (length <= newIndex && newIndex < (length + target.name.length))
444 break; 449 break;
445 length += target.name.length; 450 length += target.name.length;
446 target = target.nextSibling; 451 target = target.nextSibling;
447 } 452 }
448 if (target) { 453 if (target) {
449 newNode = target; 454 newNode = target;
450 newIndex = newIndex - length; 455 newIndex = newIndex - length;
451 } 456 }
452 break; 457 break;
453 } else if (newNode.role != RoleType.INLINE_TEXT_BOX && 458 } else if (
459 newNode.role != RoleType.INLINE_TEXT_BOX &&
454 newNode.children[newIndex]) { 460 newNode.children[newIndex]) {
455 // Valid node offset. 461 // Valid node offset.
456 newNode = newNode.children[newIndex]; 462 newNode = newNode.children[newIndex];
457 newIndex = 0; 463 newIndex = 0;
458 } else { 464 } else {
459 // Invalid offset. 465 // Invalid offset.
460 break; 466 break;
461 } 467 }
462 } 468 }
463 469
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
499 cursors.WrappingCursor.prototype = { 505 cursors.WrappingCursor.prototype = {
500 __proto__: cursors.Cursor.prototype, 506 __proto__: cursors.Cursor.prototype,
501 507
502 /** @override */ 508 /** @override */
503 move: function(unit, movement, dir) { 509 move: function(unit, movement, dir) {
504 var result = this; 510 var result = this;
505 if (!result.node) 511 if (!result.node)
506 return this; 512 return this;
507 513
508 // Regular movement. 514 // Regular movement.
509 if (!AutomationPredicate.root(this.node) || 515 if (!AutomationPredicate.root(this.node) || dir == Dir.FORWARD ||
510 dir == Dir.FORWARD ||
511 movement == Movement.BOUND) 516 movement == Movement.BOUND)
512 result = cursors.Cursor.prototype.move.call(this, unit, movement, dir); 517 result = cursors.Cursor.prototype.move.call(this, unit, movement, dir);
513 518
514 // Moving to the bounds of a unit never wraps. 519 // Moving to the bounds of a unit never wraps.
515 if (movement == Movement.BOUND) 520 if (movement == Movement.BOUND)
516 return new cursors.WrappingCursor(result.node, result.index); 521 return new cursors.WrappingCursor(result.node, result.index);
517 522
518 // There are two cases for wrapping: 523 // There are two cases for wrapping:
519 // 1. moving forwards from the last element. 524 // 1. moving forwards from the last element.
520 // 2. moving backwards from the first element. 525 // 2. moving backwards from the first element.
521 // Both result in |move| returning the same cursor. 526 // Both result in |move| returning the same cursor.
522 // For 1, simply place the new cursor on the document node. 527 // For 1, simply place the new cursor on the document node.
523 // For 2, place range on the root (if not already there). If at root, 528 // For 2, place range on the root (if not already there). If at root,
524 // try to descend to the first leaf-like object. 529 // try to descend to the first leaf-like object.
525 if (movement == Movement.DIRECTIONAL && result.equals(this)) { 530 if (movement == Movement.DIRECTIONAL && result.equals(this)) {
526 var pred = unit == Unit.NODE ? 531 var pred = unit == Unit.NODE ? AutomationPredicate.object :
527 AutomationPredicate.object : AutomationPredicate.leaf; 532 AutomationPredicate.leaf;
528 var endpoint = this.node; 533 var endpoint = this.node;
529 if (!endpoint) 534 if (!endpoint)
530 return this; 535 return this;
531 536
532 // Case 1: forwards (find the root-like node). 537 // Case 1: forwards (find the root-like node).
533 while (!AutomationPredicate.root(endpoint) && endpoint.parent) 538 while (!AutomationPredicate.root(endpoint) && endpoint.parent)
534 endpoint = endpoint.parent; 539 endpoint = endpoint.parent;
535 540
536 // Always play a wrap earcon when moving forward. 541 // Always play a wrap earcon when moving forward.
537 var playEarcon = dir == Dir.FORWARD; 542 var playEarcon = dir == Dir.FORWARD;
538 543
539 // Case 2: backward (sync downwards to a leaf), if already on the root. 544 // Case 2: backward (sync downwards to a leaf), if already on the root.
540 if (dir == Dir.BACKWARD && endpoint == this.node) { 545 if (dir == Dir.BACKWARD && endpoint == this.node) {
541 playEarcon = true; 546 playEarcon = true;
542 endpoint = AutomationUtil.findNodePre(endpoint, 547 endpoint = AutomationUtil.findNodePre(endpoint, dir, function(n) {
543 dir, 548 return pred(n) && !AutomationPredicate.shouldIgnoreNode(n);
544 function(n) { 549 }) || endpoint;
545 return pred(n) && !AutomationPredicate.shouldIgnoreNode(n);
546 }) || endpoint;
547 } 550 }
548 551
549 if (playEarcon) 552 if (playEarcon)
550 cvox.ChromeVox.earcons.playEarcon(cvox.Earcon.WRAP); 553 cvox.ChromeVox.earcons.playEarcon(cvox.Earcon.WRAP);
551 554
552 return new cursors.WrappingCursor(endpoint, cursors.NODE_INDEX); 555 return new cursors.WrappingCursor(endpoint, cursors.NODE_INDEX);
553 } 556 }
554 return new cursors.WrappingCursor(result.node, result.index); 557 return new cursors.WrappingCursor(result.node, result.index);
555 } 558 }
556 }; 559 };
(...skipping 16 matching lines...) Expand all
573 /** 576 /**
574 * Convenience method to construct a Range surrounding one node. 577 * Convenience method to construct a Range surrounding one node.
575 * @param {!AutomationNode} node 578 * @param {!AutomationNode} node
576 * @return {!cursors.Range} 579 * @return {!cursors.Range}
577 */ 580 */
578 cursors.Range.fromNode = function(node) { 581 cursors.Range.fromNode = function(node) {
579 var cursor = cursors.WrappingCursor.fromNode(node); 582 var cursor = cursors.WrappingCursor.fromNode(node);
580 return new cursors.Range(cursor, cursor); 583 return new cursors.Range(cursor, cursor);
581 }; 584 };
582 585
583 /** 586 /**
584 * Given |rangeA| and |rangeB| in order, determine which |Dir| 587 * Given |rangeA| and |rangeB| in order, determine which |Dir|
585 * relates them. 588 * relates them.
586 * @param {!cursors.Range} rangeA 589 * @param {!cursors.Range} rangeA
587 * @param {!cursors.Range} rangeB 590 * @param {!cursors.Range} rangeB
588 * @return {Dir} 591 * @return {Dir}
589 */ 592 */
590 cursors.Range.getDirection = function(rangeA, rangeB) { 593 cursors.Range.getDirection = function(rangeA, rangeB) {
591 if (!rangeA || !rangeB) 594 if (!rangeA || !rangeB)
592 return Dir.FORWARD; 595 return Dir.FORWARD;
593 596
594 if (!rangeA.start.node || !rangeA.end.node || 597 if (!rangeA.start.node || !rangeA.end.node || !rangeB.start.node ||
595 !rangeB.start.node || !rangeB.end.node) 598 !rangeB.end.node)
596 return Dir.FORWARD; 599 return Dir.FORWARD;
597 600
598 // They are the same range. 601 // They are the same range.
599 if (rangeA.start.node === rangeB.start.node && 602 if (rangeA.start.node === rangeB.start.node &&
600 rangeB.end.node === rangeA.end.node) 603 rangeB.end.node === rangeA.end.node)
601 return Dir.FORWARD; 604 return Dir.FORWARD;
602 605
603 var testDirA = 606 var testDirA =
604 AutomationUtil.getDirection( 607 AutomationUtil.getDirection(rangeA.start.node, rangeB.end.node);
605 rangeA.start.node, rangeB.end.node);
606 var testDirB = 608 var testDirB =
607 AutomationUtil.getDirection( 609 AutomationUtil.getDirection(rangeB.start.node, rangeA.end.node);
608 rangeB.start.node, rangeA.end.node);
609 610
610 // The two ranges are either partly overlapping or non overlapping. 611 // The two ranges are either partly overlapping or non overlapping.
611 if (testDirA == Dir.FORWARD && testDirB == Dir.BACKWARD) 612 if (testDirA == Dir.FORWARD && testDirB == Dir.BACKWARD)
612 return Dir.FORWARD; 613 return Dir.FORWARD;
613 else if (testDirA == Dir.BACKWARD && testDirB == Dir.FORWARD) 614 else if (testDirA == Dir.BACKWARD && testDirB == Dir.FORWARD)
614 return Dir.BACKWARD; 615 return Dir.BACKWARD;
615 else 616 else
616 return testDirA; 617 return testDirA;
617 }; 618 };
618 619
619 cursors.Range.prototype = { 620 cursors.Range.prototype = {
620 /** 621 /**
621 * Returns true if |rhs| is equal to this range. 622 * Returns true if |rhs| is equal to this range.
622 * Use this for strict equality between ranges. 623 * Use this for strict equality between ranges.
623 * @param {!cursors.Range} rhs 624 * @param {!cursors.Range} rhs
624 * @return {boolean} 625 * @return {boolean}
625 */ 626 */
626 equals: function(rhs) { 627 equals: function(rhs) {
627 return this.start_.equals(rhs.start) && 628 return this.start_.equals(rhs.start) && this.end_.equals(rhs.end);
628 this.end_.equals(rhs.end);
629 }, 629 },
630 630
631 /** 631 /**
632 * Returns true if |rhs| is equal to this range. 632 * Returns true if |rhs| is equal to this range.
633 * Use this for loose equality between ranges. 633 * Use this for loose equality between ranges.
634 * @param {!cursors.Range} rhs 634 * @param {!cursors.Range} rhs
635 * @return {boolean} 635 * @return {boolean}
636 */ 636 */
637 contentEquals: function(rhs) { 637 contentEquals: function(rhs) {
638 return this.start_.contentEquals(rhs.start) && 638 return this.start_.contentEquals(rhs.start) &&
(...skipping 22 matching lines...) Expand all
661 */ 661 */
662 get end() { 662 get end() {
663 return this.end_; 663 return this.end_;
664 }, 664 },
665 665
666 /** 666 /**
667 * Returns true if this range covers a single node's text content or less. 667 * Returns true if this range covers a single node's text content or less.
668 * @return {boolean} 668 * @return {boolean}
669 */ 669 */
670 isSubNode: function() { 670 isSubNode: function() {
671 return this.start.node === this.end.node && 671 return this.start.node === this.end.node && this.start.index > -1 &&
672 this.start.index > -1 &&
673 this.end.index > -1; 672 this.end.index > -1;
674 }, 673 },
675 674
676 /** 675 /**
677 * Returns true if this range covers inline text (i.e. each end points to an 676 * Returns true if this range covers inline text (i.e. each end points to an
678 * inlineTextBox). 677 * inlineTextBox).
679 * @return {boolean?} 678 * @return {boolean?}
680 */ 679 */
681 isInlineText: function() { 680 isInlineText: function() {
682 return this.start.node && 681 return this.start.node && this.end.node &&
683 this.end.node &&
684 this.start.node.role == this.end.node.role && 682 this.start.node.role == this.end.node.role &&
685 this.start.node.role == RoleType.INLINE_TEXT_BOX; 683 this.start.node.role == RoleType.INLINE_TEXT_BOX;
686 }, 684 },
687 685
688 /** 686 /**
689 * Makes a Range which has been moved from this range by the given unit and 687 * Makes a Range which has been moved from this range by the given unit and
690 * direction. 688 * direction.
691 * @param {Unit} unit 689 * @param {Unit} unit
692 * @param {Dir} dir 690 * @param {Dir} dir
693 * @return {cursors.Range} 691 * @return {cursors.Range}
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
726 * Select the text contained within this range. 724 * Select the text contained within this range.
727 */ 725 */
728 select: function() { 726 select: function() {
729 var startNode = this.start.selectionNode_; 727 var startNode = this.start.selectionNode_;
730 var endNode = this.end.selectionNode_; 728 var endNode = this.end.selectionNode_;
731 729
732 if (!startNode || !endNode) 730 if (!startNode || !endNode)
733 return; 731 return;
734 732
735 // Only allow selections within the same web tree. 733 // Only allow selections within the same web tree.
736 if (startNode.root && 734 if (startNode.root && startNode.root.role == RoleType.ROOT_WEB_AREA &&
737 startNode.root.role == RoleType.ROOT_WEB_AREA &&
738 startNode.root == endNode.root) { 735 startNode.root == endNode.root) {
739 // We want to adjust to select the entire node for node offsets; 736 // We want to adjust to select the entire node for node offsets;
740 // otherwise, use the plain character offset. 737 // otherwise, use the plain character offset.
741 var startIndex = this.start.selectionIndex_; 738 var startIndex = this.start.selectionIndex_;
742 var endIndex = this.end.index_ == cursors.NODE_INDEX ? 739 var endIndex = this.end.index_ == cursors.NODE_INDEX ?
743 this.end.selectionIndex_ + 1 : this.end.selectionIndex_; 740 this.end.selectionIndex_ + 1 :
741 this.end.selectionIndex_;
744 742
745 chrome.automation.setDocumentSelection( 743 chrome.automation.setDocumentSelection({
746 { anchorObject: startNode, 744 anchorObject: startNode,
747 anchorOffset: startIndex, 745 anchorOffset: startIndex,
748 focusObject: endNode, 746 focusObject: endNode,
749 focusOffset: endIndex } 747 focusOffset: endIndex
750 ); 748 });
751 } 749 }
752 }, 750 },
753 751
754 /** 752 /**
755 * Returns true if this range has either cursor end on web content. 753 * Returns true if this range has either cursor end on web content.
756 * @return {boolean} 754 * @return {boolean}
757 */ 755 */
758 isWebRange: function() { 756 isWebRange: function() {
759 return this.isValid() && 757 return this.isValid() &&
760 (this.start.node.root.role != RoleType.DESKTOP || 758 (this.start.node.root.role != RoleType.DESKTOP ||
761 this.end.node.root.role != RoleType.DESKTOP); 759 this.end.node.root.role != RoleType.DESKTOP);
762 }, 760 },
763 761
764 /** 762 /**
765 * Returns whether this range has valid start and end cursors. 763 * Returns whether this range has valid start and end cursors.
766 * @return {boolean} 764 * @return {boolean}
767 */ 765 */
768 isValid: function() { 766 isValid: function() {
769 return this.start.isValid() && this.end.isValid(); 767 return this.start.isValid() && this.end.isValid();
770 } 768 }
771 }; 769 };
772 770
773 }); // goog.scope 771 }); // goog.scope
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698