Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: Add missing media-queries and resources for PWA splash screen (#13923) (CP: 23.0) #13948

Merged
merged 1 commit into from
Jun 13, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -1754,6 +1754,13 @@ private static void setupPwa(Document document, PwaRegistry registry) {
head.appendElement(META_TAG)
.attr("name", "apple-mobile-web-app-capable")
.attr(CONTENT_ATTRIBUTE, "yes");
head.appendElement(META_TAG).attr("name", "mobile-web-app-capable")
.attr(CONTENT_ATTRIBUTE, "yes");
head.appendElement(META_TAG).attr("name", "apple-touch-fullscreen")
.attr(CONTENT_ATTRIBUTE, "yes");
head.appendElement(META_TAG)
.attr("name", "apple-mobile-web-app-title")
.attr(CONTENT_ATTRIBUTE, config.getShortName());

// Theme color
head.appendElement(META_TAG).attr("name", "theme-color")
Expand Down
9 changes: 9 additions & 0 deletions flow-server/src/main/java/com/vaadin/flow/server/PwaIcon.java
Original file line number Diff line number Diff line change
Expand Up @@ -191,6 +191,15 @@ public String getType() {
return attributes.get("type");
}

/**
* Gets the value of the {@literal rel} attribute.
*
* @return value of the {@literal rel} attribute
*/
String getRel() {
return attributes.get("rel");
}

/**
* Gets the icon {@link Domain}.
*
Expand Down
137 changes: 119 additions & 18 deletions flow-server/src/main/java/com/vaadin/flow/server/PwaRegistry.java
Original file line number Diff line number Diff line change
Expand Up @@ -68,8 +68,10 @@ public class PwaRegistry implements Serializable {
private static final String META_INF_RESOURCES = "/META-INF/resources";
private static final String HEADLESS_PROPERTY = "java.awt.headless";
private static final String APPLE_STARTUP_IMAGE = "apple-touch-startup-image";
private static final String APPLE_IMAGE_MEDIA = "(device-width: %dpx) and (device-height: %dpx) "
+ "and (-webkit-device-pixel-ratio: %d)";
private static final String APPLE_IMAGE_MEDIA = "screen and (device-width: %dpx) and (device-height: %dpx)"
+ " and (-webkit-device-pixel-ratio: %d) and (orientation: %s)";
private static final String ORIENTATION_PORTRAIT = "portrait";
private static final String ORIENTATION_LANDSCAPE = "landscape";
private static final String WORKBOX_CACHE_FORMAT = "{ url: '%s', revision: '%s' }";

private String offlineHtml = "";
Expand Down Expand Up @@ -486,25 +488,124 @@ static List<PwaIcon> getIconTemplates(String baseName) {
"apple-touch-icon", ""));

// IOS device specific splash screens
// iPhone X (1125px x 2436px)
// iPad Pro 12.9 Portrait:
icons.add(new PwaIcon(2048, 2732, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
1024, 1366, 2, ORIENTATION_PORTRAIT)));
// iPad Pro 12.9 Landscape:
icons.add(new PwaIcon(2732, 2048, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
1024, 1366, 2, ORIENTATION_LANDSCAPE)));

// iPad Pro 11, 10.5 Portrait:
icons.add(new PwaIcon(1668, 2388, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
834, 1194, 2, ORIENTATION_PORTRAIT)));
// iPad Pro 11, 10.5 Landscape:
icons.add(new PwaIcon(2388, 1668, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
834, 1194, 2, ORIENTATION_LANDSCAPE)));

// iPad Air 10.5 Portrait:
icons.add(new PwaIcon(1668, 2224, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
834, 1112, 2, ORIENTATION_PORTRAIT)));
// iPad Air 10.5 Landscape:
icons.add(new PwaIcon(2224, 1668, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
834, 1112, 2, ORIENTATION_LANDSCAPE)));

// iPad 10.2 Portrait:
icons.add(new PwaIcon(1620, 2160, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
768, 1024, 2, ORIENTATION_PORTRAIT)));
// iPad 10.2 Landscape:
icons.add(new PwaIcon(2160, 1620, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
768, 1024, 2, ORIENTATION_LANDSCAPE)));

// iPad Pro 9.7, iPad Air 9.7, iPad 9.7, iPad mini 7.9 portrait
icons.add(new PwaIcon(1536, 2048, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
768, 1024, 2, ORIENTATION_PORTRAIT)));
// iPad Pro 9.7, iPad Air 9.7, iPad 9.7, iPad mini 7.9 landscape
icons.add(new PwaIcon(2048, 1536, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
768, 1024, 2, ORIENTATION_LANDSCAPE)));

// iPhone 13 Pro Max, iPhone 12 Pro Max portrait
icons.add(new PwaIcon(1284, 2778, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
428, 926, 3, ORIENTATION_PORTRAIT)));
// iPhone 13 Pro Max, iPhone 12 Pro Max landscape
icons.add(new PwaIcon(2778, 1284, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
428, 926, 3, ORIENTATION_LANDSCAPE)));

// iPhone 13 Pro, iPhone 13, iPhone 12 Pro, iPhone 12 portrait
icons.add(new PwaIcon(1170, 2532, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
390, 844, 3, ORIENTATION_PORTRAIT)));
// iPhone 13 Pro, iPhone 13, iPhone 12 Pro, iPhone 12 landscape
icons.add(new PwaIcon(2532, 1170, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
390, 844, 3, ORIENTATION_LANDSCAPE)));

// iPhone 13 Mini, iPhone 12 Mini, iPhone 11 Pro, iPhone XS, iPhone X
// portrait
icons.add(new PwaIcon(1125, 2436, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE,
String.format(APPLE_IMAGE_MEDIA, 375, 812, 3)));

// iPhone 8, 7, 6s, 6 (750px x 1334px)
icons.add(new PwaIcon(750, 1334, baseName, PwaIcon.Domain.HEADER, false,
APPLE_STARTUP_IMAGE,
String.format(APPLE_IMAGE_MEDIA, 375, 667, 2)));

// iPhone 8 Plus, 7 Plus, 6s Plus, 6 Plus (1242px x 2208px)
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
375, 812, 3, ORIENTATION_PORTRAIT)));
// iPhone 13 Mini, iPhone 12 Mini, iPhone 11 Pro, iPhone XS, iPhone X
// landscape
icons.add(new PwaIcon(2436, 1125, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
375, 812, 3, ORIENTATION_LANDSCAPE)));

// iPhone 11 Pro Max, iPhone XS Max portrait
icons.add(new PwaIcon(1242, 2688, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
414, 896, 3, ORIENTATION_PORTRAIT)));
// iPhone 11 Pro Max, iPhone XS Max landscape
icons.add(new PwaIcon(2688, 1242, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
414, 896, 3, ORIENTATION_LANDSCAPE)));

// iPhone 11, iPhone XR portrait
icons.add(new PwaIcon(828, 1792, baseName, PwaIcon.Domain.HEADER, false,
APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA, 414, 896,
2, ORIENTATION_PORTRAIT)));
// iPhone 11, iPhone XR landscape
icons.add(new PwaIcon(1792, 828, baseName, PwaIcon.Domain.HEADER, false,
APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA, 414, 896,
2, ORIENTATION_LANDSCAPE)));

// iPhone 8 Plus, 7 Plus, 6s Plus, 6 Plus portrait
icons.add(new PwaIcon(1242, 2208, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE,
String.format(APPLE_IMAGE_MEDIA, 414, 763, 3)));

// iPhone 5 (640px x 1136px)
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
414, 736, 3, ORIENTATION_PORTRAIT)));
// iPhone 8 Plus, 7 Plus, 6s Plus, 6 Plus landscape
icons.add(new PwaIcon(2208, 1242, baseName, PwaIcon.Domain.HEADER,
false, APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA,
414, 736, 3, ORIENTATION_LANDSCAPE)));

// iPhone 8, 7, 6s, 6, SE 4.7 portrait
icons.add(new PwaIcon(750, 1334, baseName, PwaIcon.Domain.HEADER, false,
APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA, 375, 667,
2, ORIENTATION_PORTRAIT)));
// iPhone 8, 7, 6s, 6, SE 4.7 landscape
icons.add(new PwaIcon(1334, 750, baseName, PwaIcon.Domain.HEADER, false,
APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA, 375, 667,
2, ORIENTATION_LANDSCAPE)));

// iPhone 5, SE 4, iPod touch 5th Gen and later portrait
icons.add(new PwaIcon(640, 1136, baseName, PwaIcon.Domain.HEADER, false,
APPLE_STARTUP_IMAGE,
String.format(APPLE_IMAGE_MEDIA, 320, 568, 2)));
APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA, 320, 568,
2, ORIENTATION_PORTRAIT)));
// iPhone 5, SE 4, iPod touch 5th Gen and later landscape
icons.add(new PwaIcon(1136, 640, baseName, PwaIcon.Domain.HEADER, false,
APPLE_STARTUP_IMAGE, String.format(APPLE_IMAGE_MEDIA, 320, 568,
2, ORIENTATION_LANDSCAPE)));

return icons;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -631,28 +631,27 @@ public void page_configurator_append_inline_form_files()
Document page = pageBuilder.getBootstrapPage(new BootstrapContext(
request, null, session, testUI, this::contextRootRelativePath));

Elements allElements = page.head().getAllElements();
String scripts = page.getElementsByTag("script").toString();
// Note element 0 is the full head element.
assertStringEquals(
Assert.assertTrue(
"File javascript should have been appended to head element",
"<script type=\"text/javascript\">window.messages = window.messages || [];\n"
+ "window.messages.push(\"inline.js\");</script>",
allElements.get(allElements.size() - 3).toString());
assertStringEquals(
"File html should have been appended to head element",
"<script type=\"text/javascript\">\n"
scripts.contains(
"<script type=\"text/javascript\">window.messages = window.messages || [];\n"
+ "window.messages.push(\"inline.js\");</script>"));
Assert.assertTrue("File html should have been appended to head element",
scripts.contains("<script type=\"text/javascript\">\n"
+ " // document.body might not yet be accessible, so just leave a message\n"
+ " window.messages = window.messages || [];\n"
+ " window.messages.push(\"inline.html\");\n"
+ "</script>",
allElements.get(allElements.size() - 2).toString());
assertStringEquals("File css should have been appended to head element",
"<style type=\"text/css\">/* inline.css */\n" + "\n"
+ "#preloadedDiv {\n"
+ "</script>"));

String styles = page.getElementsByTag("style").toString();
Assert.assertTrue("File css should have been appended to head element",
styles.contains("<style type=\"text/css\">/* inline.css */\n"
+ "\n" + "#preloadedDiv {\n"
+ " color: rgba(255, 255, 0, 1);\n" + "}\n" + "\n"
+ "#inlineCssTestDiv {\n"
+ " color: rgba(255, 255, 0, 1);\n" + "}</style>",
allElements.get(allElements.size() - 1).toString());
+ " color: rgba(255, 255, 0, 1);\n" + "}</style>"));
}

@Test // 3036
Expand Down Expand Up @@ -982,13 +981,10 @@ public void force_wrapping_of_file()
Document page = pageBuilder.getBootstrapPage(new BootstrapContext(
request, null, session, testUI, this::contextRootRelativePath));

Elements allElements = page.head().getAllElements();

assertStringEquals(
"File css should have been prepended to body element",
"<style type=\"text/css\">window.messages = window.messages || [];\n"
+ "window.messages.push(\"inline.js\");</style>",
allElements.get(allElements.size() - 1).toString());
assertTrue("File css should have been prepended to body element",
page.getElementsByTag("style").toString().contains(
"<style type=\"text/css\">window.messages = window.messages || [];\n"
+ "window.messages.push(\"inline.js\");</style>"));
}

@Test
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -336,10 +336,32 @@ public void publicResources() {
expected.add("/icons/icon-32x32.png");
expected.add("/icons/icon-96x96.png");
expected.add("/icons/icon-180x180.png");
expected.add("/icons/icon-2048x2732.png");
expected.add("/icons/icon-2732x2048.png");
expected.add("/icons/icon-1668x2388.png");
expected.add("/icons/icon-2388x1668.png");
expected.add("/icons/icon-1668x2224.png");
expected.add("/icons/icon-2224x1668.png");
expected.add("/icons/icon-1620x2160.png");
expected.add("/icons/icon-2160x1620.png");
expected.add("/icons/icon-1536x2048.png");
expected.add("/icons/icon-2048x1536.png");
expected.add("/icons/icon-1284x2778.png");
expected.add("/icons/icon-2778x1284.png");
expected.add("/icons/icon-1170x2532.png");
expected.add("/icons/icon-2532x1170.png");
expected.add("/icons/icon-1125x2436.png");
expected.add("/icons/icon-750x1334.png");
expected.add("/icons/icon-2436x1125.png");
expected.add("/icons/icon-1242x2688.png");
expected.add("/icons/icon-2688x1242.png");
expected.add("/icons/icon-828x1792.png");
expected.add("/icons/icon-1792x828.png");
expected.add("/icons/icon-1242x2208.png");
expected.add("/icons/icon-2208x1242.png");
expected.add("/icons/icon-750x1334.png");
expected.add("/icons/icon-1334x750.png");
expected.add("/icons/icon-640x1136.png");
expected.add("/icons/icon-1136x640.png");
expected.add("/themes/**");

Set<String> actual = new HashSet<>();
Expand Down
Loading