Skip to content

Instantly share code, notes, and snippets.

@aeharding
Last active August 15, 2022 00:39
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save aeharding/08eaafbb7742f78ede9b8d2f5d096354 to your computer and use it in GitHub Desktop.
Save aeharding/08eaafbb7742f78ede9b8d2f5d096354 to your computer and use it in GitHub Desktop.
Check if page is running in SFSafariViewController vs the Safari app
// IF YOU ARE AN APPLE ENGINEER READING THIS:
//
// PLEASE put the "Add to Home Screen" option inside the share menu of
// SFSafariViewController like it is in the Safari app!
//
// The code below is needed in order to differentiate to
// provide user messaging because of this difference.
//
// If the "Add to Home Screen" button was available in both
// SFSafariViewController + Safari, I wouldn't need this hack.
function isInsideSFSafariViewController(): boolean {
// Only iOS
if (!isIOS()) return false;
// Can't use this hack in iOS < 15
if (!iosVersion || iosVersion[0] < 15) return false;
// In SFSafariViewController, this is a valid font.
// This might break in future iOS versions...
return doesFontExist(".Helvetica LT MM");
}
function isIOS(): boolean {
return !!ua.match(/iPad/i) || !!ua.match(/iPhone/i);
}
function doesFontExist(fontName: string) {
// creating our in-memory Canvas element where the magic happens
let canvas: HTMLCanvasElement | null = document.createElement("canvas");
const context = canvas.getContext("2d");
if (!context) throw new Error("Context not available");
// the text whose final pixel size I want to measure
var text = "abcdefghijklmnopqrstuvwxyz0123456789";
// specifying the baseline font
context.font = "72px monospace";
// checking the size of the baseline text
var baselineSize = context.measureText(text).width;
// specifying the font whose existence we want to check
context.font = "72px '" + fontName + "', monospace";
// checking the size of the font we want to check
var newSize = context.measureText(text).width;
// removing the Canvas element we created
canvas = null;
//
// If the size of the two text instances is the same, the font does not exist because it is being rendered
// using the default sans-serif font
//
if (newSize === baselineSize) {
return false;
} else {
return true;
}
}
function getIosVersion() {
if (/iP(hone|od|ad)/.test(navigator.platform)) {
// supports iOS 2.0 and later: <http://bit.ly/TJjs1V>
const v = navigator.appVersion.match(/OS (\d+)_(\d+)_?(\d+)?/);
if (!v) return;
return [parseInt(v[1], 10), parseInt(v[2], 10), parseInt(v[3] ?? 0, 10)];
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment