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

Side by Side Diff: ui/display/chromeos/display_configurator.cc

Issue 2427843002: Delay display configuration after waking up from suspend with multi displays (Closed)
Patch Set: derat's comments Created 4 years, 1 month 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 #include "ui/display/chromeos/display_configurator.h" 5 #include "ui/display/chromeos/display_configurator.h"
6 6
7 #include <stddef.h> 7 #include <stddef.h>
8 #include <utility> 8 #include <utility>
9 9
10 #include "base/bind.h" 10 #include "base/bind.h"
(...skipping 13 matching lines...) Expand all
24 #include "ui/display/types/display_snapshot.h" 24 #include "ui/display/types/display_snapshot.h"
25 #include "ui/display/types/native_display_delegate.h" 25 #include "ui/display/types/native_display_delegate.h"
26 #include "ui/display/util/display_util.h" 26 #include "ui/display/util/display_util.h"
27 27
28 namespace ui { 28 namespace ui {
29 29
30 namespace { 30 namespace {
31 31
32 typedef std::vector<const DisplayMode*> DisplayModeList; 32 typedef std::vector<const DisplayMode*> DisplayModeList;
33 33
34 // The delay to perform configuration after RRNotify. See the comment for
35 // |configure_timer_|.
36 const int kConfigureDelayMs = 500;
37
38 // The EDID specification marks the top bit of the manufacturer id as reserved. 34 // The EDID specification marks the top bit of the manufacturer id as reserved.
39 const int16_t kReservedManufacturerID = static_cast<int16_t>(1 << 15); 35 const int16_t kReservedManufacturerID = static_cast<int16_t>(1 << 15);
40 36
41 struct DisplayState { 37 struct DisplayState {
42 DisplaySnapshot* display = nullptr; // Not owned. 38 DisplaySnapshot* display = nullptr; // Not owned.
43 39
44 // User-selected mode for the display. 40 // User-selected mode for the display.
45 const DisplayMode* selected_mode = nullptr; 41 const DisplayMode* selected_mode = nullptr;
46 42
47 // Mode used when displaying the same desktop on multiple displays. 43 // Mode used when displaying the same desktop on multiple displays.
(...skipping 807 matching lines...) Expand 10 before | Expand all | Expand 10 after
855 !(flags & kSetDisplayPowerForceProbe)) { 851 !(flags & kSetDisplayPowerForceProbe)) {
856 callback.Run(true); 852 callback.Run(true);
857 return; 853 return;
858 } 854 }
859 855
860 pending_power_state_ = power_state; 856 pending_power_state_ = power_state;
861 has_pending_power_state_ = true; 857 has_pending_power_state_ = true;
862 pending_power_flags_ = flags; 858 pending_power_flags_ = flags;
863 queued_configuration_callbacks_.push_back(callback); 859 queued_configuration_callbacks_.push_back(callback);
864 860
861 if (configure_timer_.IsRunning()) {
862 // If there is a configuration task scheduled, avoid performing
863 // configuration immediately. Instead reset the timer to wait for things to
864 // settle.
865 configure_timer_.Reset();
866 return;
867 }
868
865 RunPendingConfiguration(); 869 RunPendingConfiguration();
866 } 870 }
867 871
868 void DisplayConfigurator::SetDisplayPower( 872 void DisplayConfigurator::SetDisplayPower(
869 chromeos::DisplayPowerState power_state, 873 chromeos::DisplayPowerState power_state,
870 int flags, 874 int flags,
871 const ConfigurationCallback& callback) { 875 const ConfigurationCallback& callback) {
872 if (!configure_display_ || display_externally_controlled_) { 876 if (!configure_display_ || display_externally_controlled_) {
873 callback.Run(false); 877 callback.Run(false);
874 return; 878 return;
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
909 // Don't do anything if the displays are currently suspended. Instead we will 913 // Don't do anything if the displays are currently suspended. Instead we will
910 // probe and reconfigure the displays if necessary in ResumeDisplays(). 914 // probe and reconfigure the displays if necessary in ResumeDisplays().
911 if (displays_suspended_) { 915 if (displays_suspended_) {
912 VLOG(1) << "Displays are currently suspended. Not attempting to " 916 VLOG(1) << "Displays are currently suspended. Not attempting to "
913 << "reconfigure them."; 917 << "reconfigure them.";
914 return; 918 return;
915 } 919 }
916 920
917 // Configure displays with |kConfigureDelayMs| delay, 921 // Configure displays with |kConfigureDelayMs| delay,
918 // so that time-consuming ConfigureDisplays() won't be called multiple times. 922 // so that time-consuming ConfigureDisplays() won't be called multiple times.
919 if (configure_timer_.IsRunning()) { 923 if (configure_timer_.IsRunning() &&
920 // Note: when the timer is running it is possible that a different task 924 configure_timer_.GetCurrentDelay() <=
921 // (RestoreRequestedPowerStateAfterResume()) is scheduled. In these cases, 925 base::TimeDelta::FromMilliseconds(kConfigureDelayMs)) {
922 // prefer the already scheduled task to ConfigureDisplays() since 926 // Avoid resetting the timer to a huge delay if we are currently pending
923 // ConfigureDisplays() performs only basic configuration while 927 // the delayed configuration after waking up from suspend.
924 // RestoreRequestedPowerStateAfterResume() will perform additional
925 // operations.
926 configure_timer_.Reset(); 928 configure_timer_.Reset();
927 } else { 929 } else {
928 configure_timer_.Start( 930 configure_timer_.Start(
929 FROM_HERE, 931 FROM_HERE,
930 base::TimeDelta::FromMilliseconds(kConfigureDelayMs), 932 base::TimeDelta::FromMilliseconds(kConfigureDelayMs),
931 this, 933 this,
932 &DisplayConfigurator::ConfigureDisplays); 934 &DisplayConfigurator::ConfigureDisplays);
933 } 935 }
934 } 936 }
935 937
(...skipping 24 matching lines...) Expand all
960 // SetDisplayPowerInternal so requested_power_state_ is maintained. 962 // SetDisplayPowerInternal so requested_power_state_ is maintained.
961 SetDisplayPowerInternal(chromeos::DISPLAY_POWER_ALL_OFF, 963 SetDisplayPowerInternal(chromeos::DISPLAY_POWER_ALL_OFF,
962 kSetDisplayPowerNoFlags, callback); 964 kSetDisplayPowerNoFlags, callback);
963 965
964 // We need to make sure that the monitor configuration we just did actually 966 // We need to make sure that the monitor configuration we just did actually
965 // completes before we return. 967 // completes before we return.
966 native_display_delegate_->SyncWithServer(); 968 native_display_delegate_->SyncWithServer();
967 } 969 }
968 970
969 void DisplayConfigurator::ResumeDisplays() { 971 void DisplayConfigurator::ResumeDisplays() {
972 ResumeDisplaysWithCallback(base::Bind(&DoNothing));
973 }
974
975 void DisplayConfigurator::ResumeDisplaysWithCallback(
976 const ConfigurationCallback& callback) {
970 if (!configure_display_ || display_externally_controlled_) 977 if (!configure_display_ || display_externally_controlled_)
Daniel Erat 2016/10/24 16:31:04 should you be running the callback here? SuspendDi
afakhry 2016/10/25 00:37:10 Done.
971 return; 978 return;
972 979
973 displays_suspended_ = false; 980 displays_suspended_ = false;
974 981
982 if (current_display_state_ == MULTIPLE_DISPLAY_STATE_DUAL_MIRROR ||
983 current_display_state_ == MULTIPLE_DISPLAY_STATE_DUAL_EXTENDED ||
984 current_display_state_ == MULTIPLE_DISPLAY_STATE_MULTI_EXTENDED) {
985 // When waking up from suspend while being in a multi display mode, we
986 // schedule a delayed forced configuration, which will make
987 // SetDisplayPowerInternal() avoid performing the configuration immediately.
988 // This gives a chance to wait for all displays to be added and detected
989 // before configuration is performed.
990 configure_timer_.Start(FROM_HERE,
991 base::TimeDelta::FromMilliseconds(
992 kResumeConfigureMultiDisplayDelayMs),
993 this,
994 &DisplayConfigurator::ConfigureDisplays);
995 }
996
975 // If requested_power_state_ is ALL_OFF due to idle suspend, powerd will turn 997 // If requested_power_state_ is ALL_OFF due to idle suspend, powerd will turn
976 // the display power on when it enables the backlight. 998 // the display power on when it enables the backlight.
977 SetDisplayPower(requested_power_state_, kSetDisplayPowerNoFlags, 999 SetDisplayPower(requested_power_state_, kSetDisplayPowerNoFlags, callback);
978 base::Bind(&DoNothing));
979 } 1000 }
980 1001
981 void DisplayConfigurator::ConfigureDisplays() { 1002 void DisplayConfigurator::ConfigureDisplays() {
982 if (!configure_display_ || display_externally_controlled_) 1003 if (!configure_display_ || display_externally_controlled_)
983 return; 1004 return;
984 1005
985 force_configure_ = true; 1006 force_configure_ = true;
986 RunPendingConfiguration(); 1007 RunPendingConfiguration();
987 } 1008 }
988 1009
(...skipping 170 matching lines...) Expand 10 before | Expand all | Expand 10 after
1159 last_virtual_display_id_ = max_display_id & 0xff; 1180 last_virtual_display_id_ = max_display_id & 0xff;
1160 1181
1161 return true; 1182 return true;
1162 } 1183 }
1163 1184
1164 bool DisplayConfigurator::IsDisplayOn() const { 1185 bool DisplayConfigurator::IsDisplayOn() const {
1165 return current_power_state_ != chromeos::DISPLAY_POWER_ALL_OFF; 1186 return current_power_state_ != chromeos::DISPLAY_POWER_ALL_OFF;
1166 } 1187 }
1167 1188
1168 } // namespace ui 1189 } // namespace ui
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698