204 lines
6.4 KiB
JavaScript
204 lines
6.4 KiB
JavaScript
// ==UserScript==
|
|
// @name Sort Videos by Like Count
|
|
// @namespace http://tampermonkey.net/
|
|
// @version 0.1
|
|
// @description Sort videos by like count on a specified website
|
|
// @author NoName
|
|
// @match https://jable.tv/*
|
|
// @match https://jable.tv
|
|
|
|
// @grant none
|
|
// ==/UserScript==
|
|
(function() {
|
|
'use strict';
|
|
|
|
// Function to extract the like count from the sub-title element
|
|
function getLikeCount(subTitleElement) {
|
|
if (subTitleElement) {
|
|
const textContent = subTitleElement.textContent.trim();
|
|
console.log('Full text content:', textContent);
|
|
|
|
// Extract all numbers from the text content
|
|
const numbers = textContent.match(/\d+/g);
|
|
if (numbers && numbers.length > 0) {
|
|
const likeCount = parseInt(numbers[numbers.length - 1].replace(/\s/g, ''), 10);
|
|
console.log('Parsed like count:', likeCount);
|
|
return isNaN(likeCount) ? 0 : likeCount;
|
|
}
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
// Function to sort the videos within each parent div
|
|
function sortVideosInParent(parent) {
|
|
console.log('Sorting videos in parent:', parent);
|
|
if (parent.classList.contains('owl-stage')) {
|
|
sortCarouselVideos(parent);
|
|
return;
|
|
}
|
|
|
|
const videos = Array.from(parent.children).map(item => {
|
|
const v = item.matches('.video-img-box') ? item : item.querySelector('.video-img-box');
|
|
if (!v) {
|
|
return null;
|
|
}
|
|
|
|
const subTitle = item.querySelector('.sub-title');
|
|
if (!subTitle) {
|
|
return null;
|
|
}
|
|
|
|
const likeCount = getLikeCount(subTitle);
|
|
console.log('Video element:', item, 'Like count:', likeCount);
|
|
return { element: item, likeCount: likeCount };
|
|
}).filter(video => video !== null);
|
|
|
|
videos.sort((a, b) => b.likeCount - a.likeCount);
|
|
|
|
videos.forEach(video => {
|
|
parent.appendChild(video.element);
|
|
});
|
|
}
|
|
|
|
function sortCarouselVideos(stage) {
|
|
const groups = Array.from(stage.children).map(group => {
|
|
const itemContainer = group.querySelector(':scope > .item');
|
|
if (!itemContainer) {
|
|
return null;
|
|
}
|
|
|
|
const cards = Array.from(itemContainer.querySelectorAll(':scope > .video-img-box'));
|
|
if (cards.length === 0) {
|
|
return null;
|
|
}
|
|
|
|
return { group, itemContainer, slotCount: cards.length, cards };
|
|
}).filter(group => group !== null);
|
|
|
|
const sortedCards = groups.flatMap(group => group.cards.map(card => {
|
|
const subTitle = card.querySelector('.sub-title');
|
|
if (!subTitle) {
|
|
return null;
|
|
}
|
|
|
|
return { element: card, likeCount: getLikeCount(subTitle) };
|
|
}).filter(card => card !== null)).sort((a, b) => b.likeCount - a.likeCount);
|
|
|
|
if (sortedCards.length < 2) {
|
|
return;
|
|
}
|
|
|
|
let index = 0;
|
|
groups.forEach(group => {
|
|
group.itemContainer.replaceChildren();
|
|
for (let i = 0; i < group.slotCount && index < sortedCards.length; i += 1) {
|
|
group.itemContainer.appendChild(sortedCards[index].element);
|
|
index += 1;
|
|
}
|
|
});
|
|
}
|
|
|
|
function getSortableParent(videoBox) {
|
|
const carouselStage = videoBox.closest('.owl-stage');
|
|
if (carouselStage) {
|
|
const sortableCards = carouselStage.querySelectorAll('.video-img-box .sub-title');
|
|
if (sortableCards.length >= 2) {
|
|
return carouselStage;
|
|
}
|
|
|
|
return null;
|
|
}
|
|
|
|
let current = videoBox;
|
|
|
|
while (current && current.parentElement) {
|
|
const parent = current.parentElement;
|
|
const sortableChildren = Array.from(parent.children).filter(child => child.matches('.video-img-box') || child.querySelector('.video-img-box'));
|
|
|
|
if (sortableChildren.length >= 2 && (current.matches('.video-img-box') || current.querySelector('.video-img-box'))) {
|
|
return parent;
|
|
}
|
|
|
|
current = parent;
|
|
}
|
|
|
|
return null;
|
|
}
|
|
|
|
// Function to find all parent divs and sort their child videos
|
|
function sortAllVideos() {
|
|
const videoContainers = document.querySelectorAll('.video-img-box');
|
|
const parents = new Set();
|
|
|
|
videoContainers.forEach(v => {
|
|
const parent = getSortableParent(v);
|
|
if (!parent) {
|
|
return;
|
|
}
|
|
|
|
console.log('Found parent:', parent);
|
|
parents.add(parent);
|
|
});
|
|
|
|
parents.forEach(parent => {
|
|
sortVideosInParent(parent);
|
|
});
|
|
}
|
|
|
|
// Add a sort button after the element with class "inactive-color fs-2 mb-0"
|
|
function addSortButton() {
|
|
const targetElement = document.querySelector('.inactive-color.fs-2.mb-0');
|
|
if (targetElement) {
|
|
const sortItem = document.createElement('li');
|
|
const sortLink = document.createElement('a');
|
|
sortLink.href = '#';
|
|
sortLink.textContent = '排序';
|
|
sortLink.style.marginLeft = '10px';
|
|
sortLink.addEventListener('click', function(event) {
|
|
event.preventDefault();
|
|
sortAllVideos();
|
|
});
|
|
sortItem.appendChild(sortLink);
|
|
|
|
targetElement.parentNode.insertBefore(sortItem, targetElement.nextSibling);
|
|
console.log('Sort button added after the target element');
|
|
}
|
|
}
|
|
|
|
|
|
// Add CSS to override the preview thumb image container dimensions
|
|
function addCustomStyles() {
|
|
if (document.getElementById('tm-preview-thumb-style')) {
|
|
return;
|
|
}
|
|
|
|
const style = document.createElement('style');
|
|
style.id = 'tm-preview-thumb-style';
|
|
style.textContent = `
|
|
:root {
|
|
--tm-preview-scale: 0.5;
|
|
}
|
|
|
|
.plyr__preview-thumb {
|
|
position: absolute !important;
|
|
left: 0px !important;
|
|
bottom: 15px !important;
|
|
top: auto !important;
|
|
right: auto !important;
|
|
transform: scale(var(--tm-preview-scale)) !important;
|
|
transform-origin: bottom left !important;
|
|
z-index: 99999 !important;
|
|
}
|
|
`;
|
|
document.head.appendChild(style);
|
|
console.log('Custom styles added for preview thumb image container');
|
|
}
|
|
|
|
// Run the sort function after the DOM content has loaded
|
|
window.addEventListener('load', function() {
|
|
addCustomStyles();
|
|
addSortButton();
|
|
sortAllVideos();
|
|
})
|
|
})();
|