OLD | NEW |
(Empty) | |
| 1 // Copyright 2016 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/banners/webapp_manifest_validator.h" |
| 6 |
| 7 #include "base/strings/string_util.h" |
| 8 #include "content/public/common/manifest.h" |
| 9 #include "ui/gfx/geometry/size.h" |
| 10 #include "url/gurl.h" |
| 11 |
| 12 namespace banners { |
| 13 namespace webapp_manifest_validator { |
| 14 |
| 15 namespace { |
| 16 |
| 17 const char kPngExtension[] = ".png"; |
| 18 |
| 19 // The requirement for now is an image/png that is at least 144x144. |
| 20 const int kIconMinimumSize = 144; |
| 21 |
| 22 bool DoesManifestContainRequiredIcon(const content::Manifest& manifest) { |
| 23 for (const auto& icon : manifest.icons) { |
| 24 // The type field is optional. If it isn't present, fall back on checking |
| 25 // the src extension, and allow the icon if the extension ends with png. |
| 26 if (!base::EqualsASCII(icon.type.string(), "image/png") && |
| 27 !(icon.type.is_null() && |
| 28 base::EndsWith(icon.src.ExtractFileName(), kPngExtension, |
| 29 base::CompareCase::INSENSITIVE_ASCII))) |
| 30 continue; |
| 31 |
| 32 for (const auto& size : icon.sizes) { |
| 33 if (size.IsEmpty()) // "any" |
| 34 return true; |
| 35 if (size.width() >= kIconMinimumSize && size.height() >= kIconMinimumSize) |
| 36 return true; |
| 37 } |
| 38 } |
| 39 |
| 40 return false; |
| 41 } |
| 42 |
| 43 } // anonymous namespace |
| 44 |
| 45 bool IsWebappCapable(const content::Manifest& manifest, |
| 46 OutputDeveloperMessageCode* code) { |
| 47 // TODO(dominickn,mlamouri): when Chrome supports "minimal-ui", it should be |
| 48 // accepted. If we accept it today, it would fallback to "browser" and make |
| 49 // this check moot. See https://crbug.com/604390 |
| 50 if (manifest.display == blink::WebDisplayModeStandalone || |
| 51 manifest.display == blink::WebDisplayModeFullscreen) { |
| 52 return true; |
| 53 } |
| 54 *code = OutputDeveloperMessageCode::kManifestDisplayStandaloneFullscreen; |
| 55 return false; |
| 56 } |
| 57 |
| 58 bool IsManifestGoodForWebapp( |
| 59 const content::Manifest& manifest, |
| 60 OutputDeveloperMessageCode* code) { |
| 61 if (manifest.IsEmpty()) { |
| 62 *code = OutputDeveloperMessageCode::kManifestEmpty; |
| 63 return false; |
| 64 } |
| 65 |
| 66 if (!IsWebappCapable(manifest, code)) { |
| 67 return false; |
| 68 } |
| 69 |
| 70 if (!manifest.start_url.is_valid()) { |
| 71 *code = OutputDeveloperMessageCode::kStartURLNotValid; |
| 72 return false; |
| 73 } |
| 74 if ((manifest.name.is_null() || manifest.name.string().empty()) && |
| 75 (manifest.short_name.is_null() || manifest.short_name.string().empty())) { |
| 76 *code = OutputDeveloperMessageCode::kManifestMissingNameOrShortName; |
| 77 return false; |
| 78 } |
| 79 |
| 80 if (!DoesManifestContainRequiredIcon(manifest)) { |
| 81 *code = OutputDeveloperMessageCode::kManifestMissingSuitableIcon; |
| 82 return false; |
| 83 } |
| 84 return true; |
| 85 } |
| 86 |
| 87 } // namespace webapp_manifest_validator |
| 88 } // namespace banners |
OLD | NEW |