mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-06-05 06:33:57 +02:00
Dynamically create / destroy videos.
This commit is contained in:
parent
7913d2a82d
commit
3e373200b1
2 changed files with 101 additions and 42 deletions
|
@ -41,6 +41,14 @@ var IV = {
|
||||||
}
|
}
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
},
|
},
|
||||||
|
getElementTop: function (element) {
|
||||||
|
var top = 0;
|
||||||
|
while (element && !element.classList.contains('page-scroll')) {
|
||||||
|
top += element.offsetTop;
|
||||||
|
element = element.offsetParent;
|
||||||
|
}
|
||||||
|
return top;
|
||||||
|
},
|
||||||
jumpToHash: function (hash, instant) {
|
jumpToHash: function (hash, instant) {
|
||||||
var current = IV.computeCurrentState();
|
var current = IV.computeCurrentState();
|
||||||
current.hash = hash;
|
current.hash = hash;
|
||||||
|
@ -55,12 +63,7 @@ var IV = {
|
||||||
|
|
||||||
var element = document.getElementsByName(hash)[0];
|
var element = document.getElementsByName(hash)[0];
|
||||||
if (element) {
|
if (element) {
|
||||||
var y = 0;
|
IV.scrollTo(IV.getElementTop(element), instant);
|
||||||
while (element && !element.classList.contains('page-scroll')) {
|
|
||||||
y += element.offsetTop;
|
|
||||||
element = element.offsetParent;
|
|
||||||
}
|
|
||||||
IV.scrollTo(y, instant);
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
frameKeyDown: function (e) {
|
frameKeyDown: function (e) {
|
||||||
|
@ -103,6 +106,7 @@ var IV = {
|
||||||
const was = IV.lastScrollTop;
|
const was = IV.lastScrollTop;
|
||||||
IV.lastScrollTop = IV.findPageScroll().scrollTop;
|
IV.lastScrollTop = IV.findPageScroll().scrollTop;
|
||||||
IV.updateJumpToTop(was < IV.lastScrollTop);
|
IV.updateJumpToTop(was < IV.lastScrollTop);
|
||||||
|
IV.checkVideos();
|
||||||
},
|
},
|
||||||
updateJumpToTop: function (scrolledDown) {
|
updateJumpToTop: function (scrolledDown) {
|
||||||
if (IV.lastScrollTop < 100) {
|
if (IV.lastScrollTop < 100) {
|
||||||
|
@ -246,9 +250,11 @@ var IV = {
|
||||||
IV.notify({ event: 'ready' });
|
IV.notify({ event: 'ready' });
|
||||||
|
|
||||||
IV.forceScrollFocus();
|
IV.forceScrollFocus();
|
||||||
|
IV.frameScrolled();
|
||||||
},
|
},
|
||||||
initMedia: function () {
|
initMedia: function () {
|
||||||
const photos = document.getElementsByClassName('photo');
|
var scroll = IV.findPageScroll();
|
||||||
|
const photos = scroll.getElementsByClassName('photo');
|
||||||
for (let i = 0; i < photos.length; ++i) {
|
for (let i = 0; i < photos.length; ++i) {
|
||||||
const photo = photos[i];
|
const photo = photos[i];
|
||||||
if (photo.classList.contains('loaded')) {
|
if (photo.classList.contains('loaded')) {
|
||||||
|
@ -265,18 +271,70 @@ var IV = {
|
||||||
}
|
}
|
||||||
img.src = url.substr(5, url.length - 7);
|
img.src = url.substr(5, url.length - 7);
|
||||||
if (img.complete) {
|
if (img.complete) {
|
||||||
img.onload();
|
photo.classList.add('loaded');
|
||||||
|
IV.stopAnimations(photo);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
const videos = document.getElementsByTagName('video');
|
IV.videos = [];
|
||||||
|
const videos = scroll.getElementsByClassName('video');
|
||||||
|
for (let i = 0; i < videos.length; ++i) {
|
||||||
|
const element = videos[i];
|
||||||
|
IV.videos.push({
|
||||||
|
element: element,
|
||||||
|
src: String(element.getAttribute('data-src')),
|
||||||
|
autoplay: (element.getAttribute('data-autoplay') == '1'),
|
||||||
|
loop: (element.getAttribute('data-loop') == '1'),
|
||||||
|
small: (element.getAttribute('data-small') == '1'),
|
||||||
|
filled: (element.firstChild
|
||||||
|
&& element.firstChild.tagName == 'VIDEO'),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
},
|
||||||
|
checkVideos: function () {
|
||||||
|
const visibleTop = IV.lastScrollTop;
|
||||||
|
const visibleBottom = visibleTop + IV.findPageScroll().offsetHeight;
|
||||||
|
const videos = IV.videos;
|
||||||
for (let i = 0; i < videos.length; ++i) {
|
for (let i = 0; i < videos.length; ++i) {
|
||||||
const video = videos[i];
|
const video = videos[i];
|
||||||
if (video.classList.contains('loaded')) {
|
const element = video.element;
|
||||||
continue;
|
const wrap = element.offsetParent; // video-wrap
|
||||||
|
const top = IV.getElementTop(wrap);
|
||||||
|
const bottom = top + wrap.offsetHeight;
|
||||||
|
if (top < visibleBottom && bottom > visibleTop) {
|
||||||
|
if (!video.filled) {
|
||||||
|
video.filled = true;
|
||||||
|
element.innerHTML = '<video muted class="'
|
||||||
|
+ (video.small ? 'video-small' : '')
|
||||||
|
+ '"'
|
||||||
|
+ (video.autoplay
|
||||||
|
? ' preload="auto" autoplay'
|
||||||
|
: (video.small
|
||||||
|
? ''
|
||||||
|
: ' controls'))
|
||||||
|
+ (video.loop ? ' loop' : '')
|
||||||
|
+ '><source src="'
|
||||||
|
+ video.src
|
||||||
|
+ '" type="video/mp4" />'
|
||||||
|
+ '</video>';
|
||||||
|
var media = element.firstChild;
|
||||||
|
const HAVE_CURRENT_DATA = 2;
|
||||||
|
if (media && media.readyState >= HAVE_CURRENT_DATA) {
|
||||||
|
media.classList.add('loaded');
|
||||||
|
IV.stopAnimations(media);
|
||||||
|
} else if (media) {
|
||||||
|
const created = new Date();
|
||||||
|
media.addEventListener('canplay', function () {
|
||||||
|
media.classList.add('loaded');
|
||||||
|
if ((new Date() - created) < 100) {
|
||||||
|
IV.stopAnimations(media);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else if (video.filled && video.autoplay) {
|
||||||
|
video.filled = false;
|
||||||
|
element.innerHTML = '';
|
||||||
}
|
}
|
||||||
video.addEventListener('canplay', function () {
|
|
||||||
video.classList.add('loaded');
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
showTooltip: function (text) {
|
showTooltip: function (text) {
|
||||||
|
@ -346,7 +404,14 @@ var IV = {
|
||||||
var to = article(IV.makeScrolledContent(data.html));
|
var to = article(IV.makeScrolledContent(data.html));
|
||||||
morphdom(from, to, {
|
morphdom(from, to, {
|
||||||
onBeforeElUpdated: function (fromEl, toEl) {
|
onBeforeElUpdated: function (fromEl, toEl) {
|
||||||
if (fromEl.classList.contains('loaded')) {
|
if (fromEl.classList.contains('video')
|
||||||
|
&& toEl.classList.contains('video')
|
||||||
|
&& fromEl.hasAttribute('data-src')
|
||||||
|
&& toEl.hasAttribute('data-src')
|
||||||
|
&& (fromEl.getAttribute('data-src')
|
||||||
|
== toEl.getAttribute('data-src'))) {
|
||||||
|
return false;
|
||||||
|
} else if (fromEl.classList.contains('loaded')) {
|
||||||
toEl.classList.add('loaded');
|
toEl.classList.add('loaded');
|
||||||
}
|
}
|
||||||
return !fromEl.isEqualNode(toEl);
|
return !fromEl.isEqualNode(toEl);
|
||||||
|
@ -466,8 +531,7 @@ var IV = {
|
||||||
|
|
||||||
now.classList.add(back ? 'hidden-left' : 'hidden-right');
|
now.classList.add(back ? 'hidden-left' : 'hidden-right');
|
||||||
now.classList.remove(back ? 'hidden-right' : 'hidden-left');
|
now.classList.remove(back ? 'hidden-right' : 'hidden-left');
|
||||||
now.firstChild.getAnimations().forEach(
|
IV.stopAnimations(now.firstChild);
|
||||||
(animation) => animation.finish());
|
|
||||||
|
|
||||||
if (!was.listening) {
|
if (!was.listening) {
|
||||||
was.listening = true;
|
was.listening = true;
|
||||||
|
@ -476,6 +540,10 @@ var IV = {
|
||||||
|| was.classList.contains('hidden-right')) {
|
|| was.classList.contains('hidden-right')) {
|
||||||
if (was.parentNode) {
|
if (was.parentNode) {
|
||||||
was.parentNode.removeChild(was);
|
was.parentNode.removeChild(was);
|
||||||
|
var videos = was.getElementsByClassName('video');
|
||||||
|
for (var i = 0; i < videos.length; ++i) {
|
||||||
|
videos[i].innerHTML = '';
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
@ -512,6 +580,7 @@ var IV = {
|
||||||
}
|
}
|
||||||
|
|
||||||
IV.forceScrollFocus();
|
IV.forceScrollFocus();
|
||||||
|
IV.frameScrolled();
|
||||||
},
|
},
|
||||||
forceScrollFocus: function () {
|
forceScrollFocus: function () {
|
||||||
IV.findPageScroll().focus();
|
IV.findPageScroll().focus();
|
||||||
|
@ -520,10 +589,17 @@ var IV = {
|
||||||
IV.findPageScroll().focus();
|
IV.findPageScroll().focus();
|
||||||
}, 100);
|
}, 100);
|
||||||
},
|
},
|
||||||
|
stopAnimations: function (element) {
|
||||||
|
element.getAnimations().forEach(
|
||||||
|
(animation) => animation.finish());
|
||||||
|
},
|
||||||
back: function () {
|
back: function () {
|
||||||
window.history.back();
|
window.history.back();
|
||||||
},
|
},
|
||||||
|
|
||||||
|
videos: {},
|
||||||
|
videosPlaying: {},
|
||||||
|
|
||||||
cache: {},
|
cache: {},
|
||||||
index: 0,
|
index: 0,
|
||||||
position: 0
|
position: 0
|
||||||
|
@ -533,6 +609,7 @@ document.onclick = IV.frameClickHandler;
|
||||||
document.onkeydown = IV.frameKeyDown;
|
document.onkeydown = IV.frameKeyDown;
|
||||||
document.onmouseenter = IV.frameMouseEnter;
|
document.onmouseenter = IV.frameMouseEnter;
|
||||||
document.onmouseup = IV.frameMouseUp;
|
document.onmouseup = IV.frameMouseUp;
|
||||||
|
document.onresize = IV.checkVideos;
|
||||||
window.onmessage = IV.postMessageHandler;
|
window.onmessage = IV.postMessageHandler;
|
||||||
window.addEventListener('popstate', function (e) {
|
window.addEventListener('popstate', function (e) {
|
||||||
if (e.state) {
|
if (e.state) {
|
||||||
|
|
|
@ -534,31 +534,13 @@ QByteArray Parser::block(
|
||||||
if (!video.id) {
|
if (!video.id) {
|
||||||
return "Video not found.";
|
return "Video not found.";
|
||||||
}
|
}
|
||||||
const auto src = documentFullUrl(video);
|
auto inner = tag("div", {
|
||||||
auto vattributes = Attributes{};
|
{ "class", "video" },
|
||||||
if (collageSmall) {
|
{ "data-src", documentFullUrl(video) },
|
||||||
vattributes.push_back({ "class", "video-small" });
|
{ "data-autoplay", data.is_autoplay() ? "1" : "0" },
|
||||||
}
|
{ "data-loop", data.is_loop() ? "1" : "0" },
|
||||||
if (data.is_autoplay()) {
|
{ "data-small", collageSmall ? "1" : "0" },
|
||||||
vattributes.push_back({ "preload", "auto" });
|
});
|
||||||
vattributes.push_back({ "autoplay", std::nullopt });
|
|
||||||
} else if (!collageSmall) {
|
|
||||||
vattributes.push_back({ "controls", std::nullopt });
|
|
||||||
}
|
|
||||||
if (data.is_loop()) {
|
|
||||||
vattributes.push_back({ "loop", std::nullopt });
|
|
||||||
}
|
|
||||||
vattributes.push_back({ "muted", std::nullopt });
|
|
||||||
auto inner = tag(
|
|
||||||
"video",
|
|
||||||
vattributes,
|
|
||||||
tag("source", { { "src", src }, { "type", "video/mp4" } }));
|
|
||||||
if (collageSmall) {
|
|
||||||
inner += tag(
|
|
||||||
"div",
|
|
||||||
{ { "class", "video-play-outer" } },
|
|
||||||
tag("div", { { "class", "video-play" } }));
|
|
||||||
}
|
|
||||||
const auto minithumb = Images::ExpandInlineBytes(video.minithumbnail);
|
const auto minithumb = Images::ExpandInlineBytes(video.minithumbnail);
|
||||||
if (!minithumb.isEmpty()) {
|
if (!minithumb.isEmpty()) {
|
||||||
const auto image = Images::Read({ .content = minithumb });
|
const auto image = Images::Read({ .content = minithumb });
|
||||||
|
|
Loading…
Add table
Reference in a new issue