// Copyright 2020 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "ash/public/cpp/ambient/fake_ambient_backend_controller_impl.h"
#include <algorithm>
#include <array>
#include <optional>
#include <utility>
#include "ash/public/cpp/ambient/ambient_backend_controller.h"
#include "ash/public/cpp/ambient/common/ambient_settings.h"
#include "ash/webui/personalization_app/mojom/personalization_app.mojom-shared.h"
#include "base/check.h"
#include "base/functional/bind.h"
#include "base/functional/callback.h"
#include "base/task/sequenced_task_runner.h"
#include "ui/gfx/geometry/size.h"
#include "url/gurl.h"
namespace ash {
namespace {
constexpr personalization_app::mojom::TopicSource kTopicSource =
personalization_app::mojom::TopicSource::kGooglePhotos;
constexpr AmbientModeTemperatureUnit kTemperatureUnit =
AmbientModeTemperatureUnit::kCelsius;
constexpr char kFakeUrl[] = "chrome://ambient";
constexpr char kFakeDetails[] = "fake-photo-attribution";
constexpr std::array<const char*, 2> kFakeBackupPhotoUrls = {
"http://fake-backup-photo-1.com", "http://fake-backup-photo-2.com"};
AmbientSettings CreateFakeSettings() {
AmbientSettings settings;
settings.topic_source = kTopicSource;
settings.temperature_unit = kTemperatureUnit;
ArtSetting art_setting0;
art_setting0.album_id = "0";
art_setting0.enabled = true;
art_setting0.title = "art0";
art_setting0.visible = true;
settings.art_settings.emplace_back(art_setting0);
ArtSetting art_setting1;
art_setting1.album_id = "1";
art_setting1.enabled = false;
art_setting1.title = "art1";
art_setting1.visible = true;
settings.art_settings.emplace_back(art_setting1);
ArtSetting hidden_setting;
hidden_setting.album_id = "2";
hidden_setting.enabled = false;
hidden_setting.title = "hidden";
hidden_setting.visible = false;
settings.art_settings.emplace_back(hidden_setting);
settings.selected_album_ids = {"1"};
return settings;
}
PersonalAlbums CreateFakeAlbums() {
PersonalAlbums albums;
PersonalAlbum album0;
album0.album_id = "0";
album0.album_name = "album0";
albums.albums.emplace_back(std::move(album0));
PersonalAlbum album1;
album1.album_id = "1";
album1.album_name = "album1";
albums.albums.emplace_back(std::move(album1));
return albums;
}
} // namespace
FakeAmbientBackendControllerImpl::FakeAmbientBackendControllerImpl() = default;
FakeAmbientBackendControllerImpl::~FakeAmbientBackendControllerImpl() = default;
void FakeAmbientBackendControllerImpl::FetchScreenUpdateInfo(
int num_topics,
bool show_pair_personal_portraits,
const gfx::Size& screen_size,
OnScreenUpdateInfoFetchedCallback callback) {
ash::ScreenUpdate update;
if (custom_topic_generator_) {
update.next_topics = custom_topic_generator_.Run(num_topics, screen_size);
} else {
int num_topics_to_return =
custom_num_topics_to_return_.has_value()
? std::min(custom_num_topics_to_return_.value(), num_topics)
: num_topics;
for (int i = 0; i < num_topics_to_return; ++i) {
ash::AmbientModeTopic topic;
topic.url = kFakeUrl;
topic.details = kFakeDetails;
topic.is_portrait = is_portrait_;
if ((show_pair_personal_portraits &&
topic_type_ == ::ambient::kPersonal && is_portrait_) ||
has_related_image_) {
topic.related_image_url = kFakeUrl;
}
topic.topic_type = topic_type_;
update.next_topics.emplace_back(topic);
}
}
// Only respond weather info when there is no active weather testing.
if (!weather_info_) {
ash::WeatherInfo weather_info;
weather_info.temp_f = .0f;
weather_info.condition_icon_url = kFakeUrl;
weather_info.show_celsius = true;
update.weather_info = weather_info;
}
// Pretend to respond asynchronously.
base::SequencedTaskRunner::GetCurrentDefault()->PostTask(
FROM_HERE, base::BindOnce(std::move(callback), update));
}
void FakeAmbientBackendControllerImpl::FetchPreviewImages(
const gfx::Size& preview_size,
OnPreviewImagesFetchedCallback callback) {
std::vector<GURL> urls = {GURL(kFakeUrl)};
// Pretend to respond asynchronously.
base::SequencedTaskRunner::GetCurrentDefault()->PostTask(
FROM_HERE, base::BindOnce(std::move(callback), urls));
}
void FakeAmbientBackendControllerImpl::UpdateSettings(
const AmbientSettings settings,
UpdateSettingsCallback callback) {
// |show_weather| should always be set to true.
DCHECK(settings.show_weather);
current_temperature_unit_ = settings.temperature_unit;
if (update_auto_reply_.has_value()) {
std::move(callback).Run(update_auto_reply_.value(), settings);
return;
}
pending_update_callback_ = std::move(callback);
pending_settings_ = settings;
}
void FakeAmbientBackendControllerImpl::FetchSettingsAndAlbums(
int banner_width,
int banner_height,
int num_albums,
OnSettingsAndAlbumsFetchedCallback callback) {
pending_fetch_settings_albums_callback_ = std::move(callback);
}
void FakeAmbientBackendControllerImpl::FetchWeather(
std::optional<std::string> weather_client_id,
bool prefer_aplha_endpoint,
FetchWeatherCallback callback) {
++fetch_weather_count_;
weather_client_id_ = weather_client_id;
if (run_fetch_weather_callback_) {
std::move(callback).Run(weather_info_);
}
}
const std::array<const char*, 2>&
FakeAmbientBackendControllerImpl::GetBackupPhotoUrls() const {
return kFakeBackupPhotoUrls;
}
std::array<const char*, 2>
FakeAmbientBackendControllerImpl::GetTimeOfDayVideoPreviewImageUrls(
AmbientVideo video) const {
return kFakeBackupPhotoUrls;
}
const char* FakeAmbientBackendControllerImpl::GetPromoBannerUrl() const {
return kFakeUrl;
}
const char* FakeAmbientBackendControllerImpl::GetTimeOfDayProductName() const {
return "Product Name";
}
void FakeAmbientBackendControllerImpl::ReplyFetchSettingsAndAlbums(
bool success,
const std::optional<AmbientSettings>& settings) {
if (!pending_fetch_settings_albums_callback_)
return;
if (success) {
std::move(pending_fetch_settings_albums_callback_)
.Run(settings.value_or(CreateFakeSettings()), CreateFakeAlbums());
} else {
std::move(pending_fetch_settings_albums_callback_)
.Run(/*settings=*/std::nullopt, PersonalAlbums());
}
}
void FakeAmbientBackendControllerImpl::SetFetchScreenUpdateInfoResponseSize(
int num_topics_to_return) {
DCHECK_GE(num_topics_to_return, 0);
custom_num_topics_to_return_.emplace(num_topics_to_return);
}
bool FakeAmbientBackendControllerImpl::IsFetchSettingsAndAlbumsPending() const {
return !pending_fetch_settings_albums_callback_.is_null();
}
void FakeAmbientBackendControllerImpl::ReplyUpdateSettings(bool success) {
if (!pending_update_callback_)
return;
std::move(pending_update_callback_).Run(success, pending_settings_);
}
bool FakeAmbientBackendControllerImpl::IsUpdateSettingsPending() const {
return !pending_update_callback_.is_null();
}
void FakeAmbientBackendControllerImpl::EnableUpdateSettingsAutoReply(
bool success) {
update_auto_reply_.emplace(success);
}
void FakeAmbientBackendControllerImpl::SetWeatherInfo(
std::optional<WeatherInfo> info) {
weather_info_ = std::move(info);
}
void FakeAmbientBackendControllerImpl::SetPhotoOrientation(bool portrait) {
is_portrait_ = portrait;
}
void FakeAmbientBackendControllerImpl::SetPhotoTopicType(
::ambient::TopicType topic_type) {
has_related_image_ = false;
topic_type_ = topic_type;
}
} // namespace ash