1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #include "chrome/browser/ui/webui/chromeos/login/user_image_screen_handler.h" 6 7 #include "base/command_line.h" 8 #include "base/logging.h" 9 #include "base/metrics/histogram.h" 10 #include "base/values.h" 11 #include "chrome/browser/chromeos/login/default_user_images.h" 12 #include "chrome/browser/chromeos/login/user.h" 13 #include "chrome/browser/chromeos/login/webui_login_display.h" 14 #include "chrome/browser/ui/webui/chromeos/login/oobe_ui.h" 15 #include "chrome/common/chrome_switches.h" 16 #include "chrome/common/url_constants.h" 17 #include "grit/generated_resources.h" 18 #include "net/base/data_url.h" 19 #include "ui/base/l10n/l10n_util.h" 20 #include "url/gurl.h" 21 22 namespace { 23 24 const char kJsScreenPath[] = "login.UserImageScreen"; 25 26 } // namespace 27 28 namespace chromeos { 29 30 UserImageScreenHandler::UserImageScreenHandler() 31 : BaseScreenHandler(kJsScreenPath), 32 screen_(NULL), 33 show_on_init_(false), 34 is_ready_(false) { 35 } 36 37 UserImageScreenHandler::~UserImageScreenHandler() { 38 if (screen_) 39 screen_->OnActorDestroyed(this); 40 } 41 42 void UserImageScreenHandler::Initialize() { 43 if (show_on_init_) { 44 Show(); 45 show_on_init_ = false; 46 } 47 } 48 49 void UserImageScreenHandler::SetDelegate( 50 UserImageScreenActor::Delegate* screen) { 51 screen_ = screen; 52 } 53 54 void UserImageScreenHandler::Show() { 55 if (!page_is_ready()) { 56 show_on_init_ = true; 57 return; 58 } 59 screen_show_time_ = base::Time::Now(); 60 ShowScreen(OobeUI::kScreenUserImagePicker, NULL); 61 62 // When shown, query camera presence. 63 if (!screen_) 64 return; 65 screen_->CheckCameraPresence(); 66 if (is_ready_) 67 screen_->OnScreenReady(); 68 } 69 70 void UserImageScreenHandler::Hide() { 71 } 72 73 void UserImageScreenHandler::PrepareToShow() { 74 } 75 76 void UserImageScreenHandler::DeclareLocalizedValues( 77 LocalizedValuesBuilder* builder) { 78 // TODO(ivankr): string should be renamed to something like 79 // IDS_USER_IMAGE_SCREEN_TITLE (currently used for Take Photo dialog). 80 builder->Add("userImageScreenTitle", IDS_OOBE_PICTURE); 81 builder->Add("userImageScreenDescription", 82 IDS_OPTIONS_CHANGE_PICTURE_DIALOG_TEXT); 83 builder->Add("takePhoto", IDS_OPTIONS_CHANGE_PICTURE_TAKE_PHOTO); 84 builder->Add("discardPhoto", IDS_OPTIONS_CHANGE_PICTURE_DISCARD_PHOTO); 85 builder->Add("flipPhoto", IDS_OPTIONS_CHANGE_PICTURE_FLIP_PHOTO); 86 builder->Add("profilePhoto", IDS_IMAGE_SCREEN_PROFILE_PHOTO); 87 builder->Add("profilePhotoLoading", 88 IDS_IMAGE_SCREEN_PROFILE_LOADING_PHOTO); 89 builder->Add("okButtonText", IDS_OK); 90 builder->Add("authorCredit", IDS_OPTIONS_SET_WALLPAPER_AUTHOR_TEXT); 91 builder->Add("photoFromCamera", IDS_OPTIONS_CHANGE_PICTURE_PHOTO_FROM_CAMERA); 92 builder->Add("photoCaptureAccessibleText", 93 IDS_OPTIONS_PHOTO_CAPTURE_ACCESSIBLE_TEXT); 94 builder->Add("photoDiscardAccessibleText", 95 IDS_OPTIONS_PHOTO_DISCARD_ACCESSIBLE_TEXT); 96 builder->Add("syncingPreferences", IDS_IMAGE_SCREEN_SYNCING_PREFERENCES); 97 } 98 99 void UserImageScreenHandler::RegisterMessages() { 100 AddCallback("getImages", &UserImageScreenHandler::HandleGetImages); 101 AddCallback("screenReady", &UserImageScreenHandler::HandleScreenReady); 102 AddCallback("photoTaken", &UserImageScreenHandler::HandlePhotoTaken); 103 AddCallback("selectImage", &UserImageScreenHandler::HandleSelectImage); 104 AddCallback("checkCameraPresence", 105 &UserImageScreenHandler::HandleCheckCameraPresence); 106 AddCallback("onUserImageAccepted", 107 &UserImageScreenHandler::HandleImageAccepted); 108 AddCallback("onUserImageScreenShown", 109 &UserImageScreenHandler::HandleScreenShown); 110 } 111 112 void UserImageScreenHandler::SelectImage(int index) { 113 if (page_is_ready()) 114 CallJS("setSelectedImage", GetDefaultImageUrl(index)); 115 } 116 117 void UserImageScreenHandler::SendProfileImage(const std::string& data_url) { 118 if (page_is_ready()) 119 CallJS("setProfileImage", data_url); 120 } 121 122 void UserImageScreenHandler::OnProfileImageAbsent() { 123 if (page_is_ready()) { 124 scoped_ptr<base::Value> null_value(base::Value::CreateNullValue()); 125 CallJS("setProfileImage", *null_value); 126 } 127 } 128 129 // TODO(antrim) : It looks more like parameters for "Init" rather than callback. 130 void UserImageScreenHandler::HandleGetImages() { 131 base::ListValue image_urls; 132 for (int i = kFirstDefaultImageIndex; i < kDefaultImagesCount; ++i) { 133 scoped_ptr<base::DictionaryValue> image_data(new base::DictionaryValue); 134 image_data->SetString("url", GetDefaultImageUrl(i)); 135 image_data->SetString( 136 "author", l10n_util::GetStringUTF16(kDefaultImageAuthorIDs[i])); 137 image_data->SetString( 138 "website", l10n_util::GetStringUTF16(kDefaultImageWebsiteIDs[i])); 139 image_data->SetString("title", GetDefaultImageDescription(i)); 140 image_urls.Append(image_data.release()); 141 } 142 CallJS("setDefaultImages", image_urls); 143 if (!screen_) 144 return; 145 if (screen_->selected_image() != User::kInvalidImageIndex) 146 SelectImage(screen_->selected_image()); 147 148 if (screen_->profile_picture_data_url() != content::kAboutBlankURL) 149 SendProfileImage(screen_->profile_picture_data_url()); 150 else if (screen_->profile_picture_absent()) 151 OnProfileImageAbsent(); 152 } 153 154 void UserImageScreenHandler::HandleScreenReady() { 155 is_ready_ = true; 156 if (screen_) 157 screen_->OnScreenReady(); 158 } 159 160 void UserImageScreenHandler::HandlePhotoTaken(const std::string& image_url) { 161 std::string mime_type, charset, raw_data; 162 if (!net::DataURL::Parse(GURL(image_url), &mime_type, &charset, &raw_data)) 163 NOTREACHED(); 164 DCHECK_EQ("image/png", mime_type); 165 166 if (screen_) 167 screen_->OnPhotoTaken(raw_data); 168 } 169 170 void UserImageScreenHandler::HandleCheckCameraPresence() { 171 if (!screen_) 172 return; 173 screen_->CheckCameraPresence(); 174 } 175 176 void UserImageScreenHandler::HandleSelectImage(const std::string& image_url, 177 const std::string& image_type, 178 bool is_user_selection) { 179 if (screen_) 180 screen_->OnImageSelected(image_type, image_url, is_user_selection); 181 } 182 183 void UserImageScreenHandler::HandleImageAccepted() { 184 if (screen_) 185 screen_->OnImageAccepted(); 186 } 187 188 void UserImageScreenHandler::HandleScreenShown() { 189 DCHECK(!screen_show_time_.is_null()); 190 191 base::TimeDelta delta = base::Time::Now() - screen_show_time_; 192 VLOG(1) << "Screen load time: " << delta.InSecondsF(); 193 UMA_HISTOGRAM_TIMES("UserImage.ScreenIsShownTime", delta); 194 } 195 196 void UserImageScreenHandler::SetCameraPresent(bool present) { 197 CallJS("setCameraPresent", present); 198 } 199 200 void UserImageScreenHandler::HideCurtain() { 201 CallJS("hideCurtain"); 202 } 203 204 void UserImageScreenHandler::SetProfilePictureEnabled(bool enabled) { 205 CallJS("setProfilePictureEnabled", enabled); 206 } 207 208 } // namespace chromeos 209