OLD | NEW |
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 #include "platform/scheduler/renderer/renderer_scheduler_impl.h" | 5 #include "platform/scheduler/renderer/renderer_scheduler_impl.h" |
6 | 6 |
7 #include "base/bind.h" | 7 #include "base/bind.h" |
8 #include "base/debug/stack_trace.h" | 8 #include "base/debug/stack_trace.h" |
9 #include "base/logging.h" | 9 #include "base/logging.h" |
10 #include "base/memory/ptr_util.h" | 10 #include "base/memory/ptr_util.h" |
(...skipping 450 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
461 | 461 |
462 bool RendererSchedulerImpl::PolicyNeedsUpdateForTesting() { | 462 bool RendererSchedulerImpl::PolicyNeedsUpdateForTesting() { |
463 return policy_may_need_update_.IsSet(); | 463 return policy_may_need_update_.IsSet(); |
464 } | 464 } |
465 | 465 |
466 // static | 466 // static |
467 bool RendererSchedulerImpl::ShouldPrioritizeInputEvent( | 467 bool RendererSchedulerImpl::ShouldPrioritizeInputEvent( |
468 const blink::WebInputEvent& web_input_event) { | 468 const blink::WebInputEvent& web_input_event) { |
469 // We regard MouseMove events with the left mouse button down as a signal | 469 // We regard MouseMove events with the left mouse button down as a signal |
470 // that the user is doing something requiring a smooth frame rate. | 470 // that the user is doing something requiring a smooth frame rate. |
471 if (web_input_event.type == blink::WebInputEvent::MouseMove && | 471 if ((web_input_event.type == blink::WebInputEvent::MouseDown || |
| 472 web_input_event.type == blink::WebInputEvent::MouseMove) && |
472 (web_input_event.modifiers & blink::WebInputEvent::LeftButtonDown)) { | 473 (web_input_event.modifiers & blink::WebInputEvent::LeftButtonDown)) { |
473 return true; | 474 return true; |
474 } | 475 } |
475 // Ignore all other mouse events because they probably don't signal user | 476 // Ignore all other mouse events because they probably don't signal user |
476 // interaction needing a smooth framerate. NOTE isMouseEventType returns false | 477 // interaction needing a smooth framerate. NOTE isMouseEventType returns false |
477 // for mouse wheel events, hence we regard them as user input. | 478 // for mouse wheel events, hence we regard them as user input. |
478 // Ignore keyboard events because it doesn't really make sense to enter | 479 // Ignore keyboard events because it doesn't really make sense to enter |
479 // compositor priority for them. | 480 // compositor priority for them. |
480 if (blink::WebInputEvent::isMouseEventType(web_input_event.type) || | 481 if (blink::WebInputEvent::isMouseEventType(web_input_event.type) || |
481 blink::WebInputEvent::isKeyboardEventType(web_input_event.type)) { | 482 blink::WebInputEvent::isKeyboardEventType(web_input_event.type)) { |
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
521 UseCase previous_use_case = | 522 UseCase previous_use_case = |
522 ComputeCurrentUseCase(now, &unused_policy_duration); | 523 ComputeCurrentUseCase(now, &unused_policy_duration); |
523 bool was_awaiting_touch_start_response = | 524 bool was_awaiting_touch_start_response = |
524 AnyThread().awaiting_touch_start_response; | 525 AnyThread().awaiting_touch_start_response; |
525 | 526 |
526 AnyThread().user_model.DidStartProcessingInputEvent(type, now); | 527 AnyThread().user_model.DidStartProcessingInputEvent(type, now); |
527 | 528 |
528 if (input_event_state == InputEventState::EVENT_CONSUMED_BY_COMPOSITOR) | 529 if (input_event_state == InputEventState::EVENT_CONSUMED_BY_COMPOSITOR) |
529 AnyThread().user_model.DidFinishProcessingInputEvent(now); | 530 AnyThread().user_model.DidFinishProcessingInputEvent(now); |
530 | 531 |
531 if (type) { | 532 switch (type) { |
532 switch (type) { | 533 case blink::WebInputEvent::TouchStart: |
533 case blink::WebInputEvent::TouchStart: | 534 AnyThread().awaiting_touch_start_response = true; |
534 AnyThread().awaiting_touch_start_response = true; | 535 // This is just a fail-safe to reset the state of |
535 // This is just a fail-safe to reset the state of | 536 // |last_gesture_was_compositor_driven| to the default. We don't know |
536 // |last_gesture_was_compositor_driven| to the default. We don't know | 537 // yet where the gesture will run. |
537 // yet where the gesture will run. | 538 AnyThread().last_gesture_was_compositor_driven = false; |
538 AnyThread().last_gesture_was_compositor_driven = false; | 539 AnyThread().have_seen_touchstart = true; |
539 AnyThread().have_seen_touchstart = true; | 540 // Assume the default gesture is prevented until we see evidence |
540 // Assume the default gesture is prevented until we see evidence | 541 // otherwise. |
541 // otherwise. | 542 AnyThread().default_gesture_prevented = true; |
542 AnyThread().default_gesture_prevented = true; | 543 break; |
543 break; | |
544 | 544 |
545 case blink::WebInputEvent::TouchMove: | 545 case blink::WebInputEvent::TouchMove: |
546 // Observation of consecutive touchmoves is a strong signal that the | 546 // Observation of consecutive touchmoves is a strong signal that the |
547 // page is consuming the touch sequence, in which case touchstart | 547 // page is consuming the touch sequence, in which case touchstart |
548 // response prioritization is no longer necessary. Otherwise, the | 548 // response prioritization is no longer necessary. Otherwise, the |
549 // initial touchmove should preserve the touchstart response pending | 549 // initial touchmove should preserve the touchstart response pending |
550 // state. | 550 // state. |
551 if (AnyThread().awaiting_touch_start_response && | 551 if (AnyThread().awaiting_touch_start_response && |
552 CompositorThreadOnly().last_input_type == | 552 CompositorThreadOnly().last_input_type == |
553 blink::WebInputEvent::TouchMove) { | 553 blink::WebInputEvent::TouchMove) { |
554 AnyThread().awaiting_touch_start_response = false; | 554 AnyThread().awaiting_touch_start_response = false; |
555 } | 555 } |
556 break; | 556 break; |
557 | 557 |
558 case blink::WebInputEvent::GesturePinchUpdate: | 558 case blink::WebInputEvent::GesturePinchUpdate: |
559 case blink::WebInputEvent::GestureScrollUpdate: | 559 case blink::WebInputEvent::GestureScrollUpdate: |
560 // If we see events for an established gesture, we can lock it to the | 560 // If we see events for an established gesture, we can lock it to the |
561 // appropriate thread as the gesture can no longer be cancelled. | 561 // appropriate thread as the gesture can no longer be cancelled. |
562 AnyThread().last_gesture_was_compositor_driven = | 562 AnyThread().last_gesture_was_compositor_driven = |
563 input_event_state == InputEventState::EVENT_CONSUMED_BY_COMPOSITOR; | 563 input_event_state == InputEventState::EVENT_CONSUMED_BY_COMPOSITOR; |
564 AnyThread().awaiting_touch_start_response = false; | 564 AnyThread().awaiting_touch_start_response = false; |
565 AnyThread().default_gesture_prevented = false; | 565 AnyThread().default_gesture_prevented = false; |
566 break; | 566 break; |
567 | 567 |
568 case blink::WebInputEvent::GestureFlingCancel: | 568 case blink::WebInputEvent::GestureFlingCancel: |
569 AnyThread().fling_compositor_escalation_deadline = base::TimeTicks(); | 569 AnyThread().fling_compositor_escalation_deadline = base::TimeTicks(); |
570 break; | 570 break; |
571 | 571 |
572 case blink::WebInputEvent::GestureTapDown: | 572 case blink::WebInputEvent::GestureTapDown: |
573 case blink::WebInputEvent::GestureShowPress: | 573 case blink::WebInputEvent::GestureShowPress: |
574 case blink::WebInputEvent::GestureScrollEnd: | 574 case blink::WebInputEvent::GestureScrollEnd: |
575 // With no observable effect, these meta events do not indicate a | 575 // With no observable effect, these meta events do not indicate a |
576 // meaningful touchstart response and should not impact task priority. | 576 // meaningful touchstart response and should not impact task priority. |
577 break; | 577 break; |
578 | 578 |
579 default: | 579 case blink::WebInputEvent::MouseDown: |
580 AnyThread().awaiting_touch_start_response = false; | 580 // Reset tracking state at the start of a new mouse drag gesture. |
581 break; | 581 AnyThread().last_gesture_was_compositor_driven = false; |
582 } | 582 AnyThread().default_gesture_prevented = true; |
| 583 break; |
| 584 |
| 585 case blink::WebInputEvent::MouseMove: |
| 586 // Consider mouse movement with the left button held down (see |
| 587 // ShouldPrioritizeInputEvent) similarly to a touch gesture. |
| 588 AnyThread().last_gesture_was_compositor_driven = |
| 589 input_event_state == InputEventState::EVENT_CONSUMED_BY_COMPOSITOR; |
| 590 AnyThread().awaiting_touch_start_response = false; |
| 591 break; |
| 592 |
| 593 case blink::WebInputEvent::Undefined: |
| 594 break; |
| 595 |
| 596 default: |
| 597 AnyThread().awaiting_touch_start_response = false; |
| 598 break; |
583 } | 599 } |
584 | 600 |
585 // Avoid unnecessary policy updates if the use case did not change. | 601 // Avoid unnecessary policy updates if the use case did not change. |
586 UseCase use_case = ComputeCurrentUseCase(now, &unused_policy_duration); | 602 UseCase use_case = ComputeCurrentUseCase(now, &unused_policy_duration); |
587 | 603 |
588 if (use_case != previous_use_case || | 604 if (use_case != previous_use_case || |
589 was_awaiting_touch_start_response != | 605 was_awaiting_touch_start_response != |
590 AnyThread().awaiting_touch_start_response) { | 606 AnyThread().awaiting_touch_start_response) { |
591 EnsureUrgentPolicyUpdatePostedOnMainThread(FROM_HERE); | 607 EnsureUrgentPolicyUpdatePostedOnMainThread(FROM_HERE); |
592 } | 608 } |
(...skipping 419 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1012 // Yes a gesture has been established. Based on how the gesture is handled | 1028 // Yes a gesture has been established. Based on how the gesture is handled |
1013 // we need to choose between one of four use cases: | 1029 // we need to choose between one of four use cases: |
1014 // 1. COMPOSITOR_GESTURE where the gesture is processed only on the | 1030 // 1. COMPOSITOR_GESTURE where the gesture is processed only on the |
1015 // compositor thread. | 1031 // compositor thread. |
1016 // 2. MAIN_THREAD_GESTURE where the gesture is processed only on the main | 1032 // 2. MAIN_THREAD_GESTURE where the gesture is processed only on the main |
1017 // thread. | 1033 // thread. |
1018 // 3. MAIN_THREAD_CUSTOM_INPUT_HANDLING where the main thread processes a | 1034 // 3. MAIN_THREAD_CUSTOM_INPUT_HANDLING where the main thread processes a |
1019 // stream of input events and has prevented a default gesture from being | 1035 // stream of input events and has prevented a default gesture from being |
1020 // started. | 1036 // started. |
1021 // 4. SYNCHRONIZED_GESTURE where the gesture is processed on both threads. | 1037 // 4. SYNCHRONIZED_GESTURE where the gesture is processed on both threads. |
1022 // TODO(skyostil): Consider removing in_idle_period_ and | |
1023 // HadAnIdlePeriodRecently() unless we need them here. | |
1024 if (AnyThread().last_gesture_was_compositor_driven) { | 1038 if (AnyThread().last_gesture_was_compositor_driven) { |
1025 if (AnyThread().begin_main_frame_on_critical_path) { | 1039 if (AnyThread().begin_main_frame_on_critical_path) { |
1026 return UseCase::SYNCHRONIZED_GESTURE; | 1040 return UseCase::SYNCHRONIZED_GESTURE; |
1027 } else { | 1041 } else { |
1028 return UseCase::COMPOSITOR_GESTURE; | 1042 return UseCase::COMPOSITOR_GESTURE; |
1029 } | 1043 } |
1030 } | 1044 } |
1031 if (AnyThread().default_gesture_prevented) { | 1045 if (AnyThread().default_gesture_prevented) { |
1032 return UseCase::MAIN_THREAD_CUSTOM_INPUT_HANDLING; | 1046 return UseCase::MAIN_THREAD_CUSTOM_INPUT_HANDLING; |
1033 } else { | 1047 } else { |
(...skipping 240 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1274 TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("renderer.scheduler"), | 1288 TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("renderer.scheduler"), |
1275 "RendererSchedulerImpl::OnNavigationStarted"); | 1289 "RendererSchedulerImpl::OnNavigationStarted"); |
1276 base::AutoLock lock(any_thread_lock_); | 1290 base::AutoLock lock(any_thread_lock_); |
1277 AnyThread().rails_loading_priority_deadline = | 1291 AnyThread().rails_loading_priority_deadline = |
1278 helper_.scheduler_tqm_delegate()->NowTicks() + | 1292 helper_.scheduler_tqm_delegate()->NowTicks() + |
1279 base::TimeDelta::FromMilliseconds( | 1293 base::TimeDelta::FromMilliseconds( |
1280 kRailsInitialLoadingPrioritizationMillis); | 1294 kRailsInitialLoadingPrioritizationMillis); |
1281 ResetForNavigationLocked(); | 1295 ResetForNavigationLocked(); |
1282 } | 1296 } |
1283 | 1297 |
1284 bool RendererSchedulerImpl::HadAnIdlePeriodRecently(base::TimeTicks now) const { | |
1285 return (now - AnyThread().last_idle_period_end_time) <= | |
1286 base::TimeDelta::FromMilliseconds( | |
1287 kIdlePeriodStarvationThresholdMillis); | |
1288 } | |
1289 | |
1290 void RendererSchedulerImpl::SuspendTimerQueueWhenBackgrounded() { | 1298 void RendererSchedulerImpl::SuspendTimerQueueWhenBackgrounded() { |
1291 DCHECK(MainThreadOnly().renderer_backgrounded); | 1299 DCHECK(MainThreadOnly().renderer_backgrounded); |
1292 if (MainThreadOnly().timer_queue_suspended_when_backgrounded) | 1300 if (MainThreadOnly().timer_queue_suspended_when_backgrounded) |
1293 return; | 1301 return; |
1294 | 1302 |
1295 MainThreadOnly().timer_queue_suspended_when_backgrounded = true; | 1303 MainThreadOnly().timer_queue_suspended_when_backgrounded = true; |
1296 ForceUpdatePolicy(); | 1304 ForceUpdatePolicy(); |
1297 } | 1305 } |
1298 | 1306 |
1299 void RendererSchedulerImpl::ResumeTimerQueueWhenForegrounded() { | 1307 void RendererSchedulerImpl::ResumeTimerQueueWhenForegrounded() { |
(...skipping 188 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1488 case v8::PERFORMANCE_LOAD: | 1496 case v8::PERFORMANCE_LOAD: |
1489 return "load"; | 1497 return "load"; |
1490 default: | 1498 default: |
1491 NOTREACHED(); | 1499 NOTREACHED(); |
1492 return nullptr; | 1500 return nullptr; |
1493 } | 1501 } |
1494 } | 1502 } |
1495 | 1503 |
1496 } // namespace scheduler | 1504 } // namespace scheduler |
1497 } // namespace blink | 1505 } // namespace blink |
OLD | NEW |