Add iOS pull-to-refresh and PNG app icons
This commit is contained in:
@@ -992,6 +992,125 @@
|
||||
return window.matchMedia("(display-mode: standalone)").matches || window.navigator.standalone === true;
|
||||
}
|
||||
|
||||
function isAppleTouchDevice() {
|
||||
return /iPhone|iPad|iPod/i.test(window.navigator.userAgent)
|
||||
|| (window.navigator.platform === "MacIntel" && window.navigator.maxTouchPoints > 1);
|
||||
}
|
||||
|
||||
function initPullToRefresh() {
|
||||
if (!isStandaloneMode() || !isAppleTouchDevice()) {
|
||||
return;
|
||||
}
|
||||
|
||||
const indicator = document.querySelector("[data-pull-refresh-indicator]");
|
||||
const body = document.body;
|
||||
const threshold = 96;
|
||||
let isTracking = false;
|
||||
let isReady = false;
|
||||
let startY = 0;
|
||||
|
||||
const setIndicator = message => {
|
||||
if (indicator) {
|
||||
indicator.textContent = message;
|
||||
}
|
||||
};
|
||||
|
||||
const resetState = () => {
|
||||
body.classList.remove("is-pull-refreshing", "is-pull-refresh-ready");
|
||||
isTracking = false;
|
||||
isReady = false;
|
||||
startY = 0;
|
||||
setIndicator("Zum Aktualisieren ziehen");
|
||||
};
|
||||
|
||||
const scrollTop = () => Math.max(
|
||||
window.scrollY || 0,
|
||||
document.documentElement.scrollTop || 0,
|
||||
document.body.scrollTop || 0
|
||||
);
|
||||
|
||||
const canStart = target => {
|
||||
if (scrollTop() > 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!(target instanceof Element)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return !target.closest("input, textarea, select, button");
|
||||
};
|
||||
|
||||
window.addEventListener("touchstart", event => {
|
||||
if (event.touches.length !== 1 || !canStart(event.target)) {
|
||||
resetState();
|
||||
return;
|
||||
}
|
||||
|
||||
isTracking = true;
|
||||
startY = event.touches[0].clientY;
|
||||
}, { passive: true });
|
||||
|
||||
window.addEventListener("touchmove", event => {
|
||||
if (!isTracking || event.touches.length !== 1) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (scrollTop() > 0) {
|
||||
resetState();
|
||||
return;
|
||||
}
|
||||
|
||||
const delta = event.touches[0].clientY - startY;
|
||||
|
||||
if (delta <= 0) {
|
||||
body.classList.remove("is-pull-refreshing", "is-pull-refresh-ready");
|
||||
isReady = false;
|
||||
setIndicator("Zum Aktualisieren ziehen");
|
||||
return;
|
||||
}
|
||||
|
||||
if (delta > 18) {
|
||||
body.classList.add("is-pull-refreshing");
|
||||
event.preventDefault();
|
||||
}
|
||||
|
||||
if (delta >= threshold) {
|
||||
if (!isReady) {
|
||||
body.classList.add("is-pull-refresh-ready");
|
||||
setIndicator("Loslassen zum Aktualisieren");
|
||||
isReady = true;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (isReady) {
|
||||
body.classList.remove("is-pull-refresh-ready");
|
||||
isReady = false;
|
||||
}
|
||||
|
||||
setIndicator("Zum Aktualisieren ziehen");
|
||||
}, { passive: false });
|
||||
|
||||
window.addEventListener("touchend", () => {
|
||||
if (!isTracking) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (isReady) {
|
||||
body.classList.remove("is-pull-refreshing", "is-pull-refresh-ready");
|
||||
body.classList.add("is-pull-refresh-reloading");
|
||||
setIndicator("Wird aktualisiert ...");
|
||||
window.location.reload();
|
||||
return;
|
||||
}
|
||||
|
||||
resetState();
|
||||
}, { passive: true });
|
||||
|
||||
window.addEventListener("touchcancel", resetState, { passive: true });
|
||||
}
|
||||
|
||||
function initPushControls() {
|
||||
const panel = document.querySelector("[data-push-panel]");
|
||||
if (!panel) {
|
||||
@@ -1147,5 +1266,6 @@
|
||||
initDashboardCharts();
|
||||
initSportTypeManager();
|
||||
initPwaShell();
|
||||
initPullToRefresh();
|
||||
initPushControls();
|
||||
})();
|
||||
|
||||
Reference in New Issue
Block a user