Skip to content

Commit

Permalink
A lot of improvements that make the app more reliable and more usable.
Browse files Browse the repository at this point in the history
- Now relies on [Stremio Service](https://github.com/Stremio/stremio-service) to run (if stremio service isn't installed it will guide the user to install it). This is means you will get a similar streaming experience to the official app.
- Checks if the installed version is the latest version or not. Startup checking can be disabled from the settings (not tested yet).
- Made a new plugin called "BetterEpisodesList." The idea is to add a new season option in shows that says "all." When the option is chosen, the plugin will take all of the episodes available in a show (except specials) and put them in one list for you, numbered as they are in one list. This is very useful for shows like One Piece, Where in other platforms the episodes are listed as they are in one season. This plugin brings that to Stremio. The plugin also adds a search bar for the user to search episodes, which is a feature apparent in [Stremio Web](https://web.stremio.com/).
- Now shows the list of plugins/themes in more details. It will show the details provided in the meta data (the first few comment lines). You can check examples/BetterEpisodesList.plugin.js.
- The source is a bit more organized now.
- Fixed the flag for --devtools. Now if the user launches stremio-enhanced with the flag --devtools it will open the F12 devtools on launch properly.
- Added the hotkey Ctrl+Shift+I to open the devtools.
- Added the flag --no-stremio-service for users who don't want to use stremio service and override the streaming server URL from the settings.
- Now sets the background to black on startup, so you don't get flashbanged on launch.
*Note: I've only tested the update on Windows.*
  • Loading branch information
REVENGE977 committed Jan 18, 2024
1 parent dd1752c commit ff3cb78
Show file tree
Hide file tree
Showing 21 changed files with 20,589 additions and 165,877 deletions.
63 changes: 35 additions & 28 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,47 +5,54 @@
<h1 align="center">[WIP] Stremio Enhanced</h1>

## What is stremio enhanced ?
basically a stremio client with plugins and themes support,
it runs the stremio streaming server and opens this [url](https://app.strem.io/shell-v4.4) in electron (i know its probably not the best way to do it, but thats just how i got it working).
Basically a stremio client with plugins and themes support,
it runs the stremio service automatically and opens this [url](https://app.strem.io/shell-v4.4) in an electron app.

with this project you can make stremio look like this:
With this project you can make stremio look like this, for example:
![screenshot](https://github.com/REVENGE977/stremio-enhanced/raw/main/images/amoled_screenshot.png)

this theme can be found [here](https://github.com/REVENGE977/stremio-enhanced-community/blob/main/examples/amoled.theme.css),
this theme can be found [here](https://github.com/REVENGE977/stremio-enhanced-community/blob/main/examples/amoled.theme.css).
## Downloads
you can download the latest version from [here](https://github.com/REVENGE977/stremio-enhanced/releases)
or build it yourself
You can download the latest version from [here](https://github.com/REVENGE977/stremio-enhanced/releases), or build it yourself:
```
git clone https://github.com/REVENGE977/stremio-enhanced.git
cd stremio-enhanced
npm run package-win32
```

## How do i install themes/plugins ?
just go to the settings and scroll down and you should see a "OPEN THEMES FOLDER" button
## How do I install themes/plugins?
Just go to the settings and scroll down and you should see a "OPEN THEMES FOLDER" button
click on it and it should open the themes folder to install themes simply move your theme into that folder
and when you restart stremio enhanced you should be able to see your theme in the settings and a button to apply that theme.

same for plugins, you just click on "OPEN PLUGINS FOLDER" and move your plugin into the plugins folder.
![settings_screenshot](https://github.com/REVENGE977/stremio-enhanced/raw/main/images/settings_screenshot.png)

## How do i make my own plugin ?
plugins are simply javascript files running on the client-side, so just write your javascript code like you normally would on client-side
and add .plugin.js at the end of the javascript file name, and move your javascript plugin to the plugins folder (%appdata%\stremio-enhanced\plugins)

## How do i make my own theme ?
you just take the stock stremio css file and modify it
the stock css file can be found [here](https://github.com/REVENGE977/stremio-enhanced-community/blob/main/examples/stockstremio_unminified.theme.css)

## Videos wont load ?
try this:
[download ffmpeg](https://github.com/BtbN/FFmpeg-Builds/releases/download/latest/ffmpeg-master-latest-win64-gpl.zip) and put it in the stremio-enhanced folder (you only need ffmpeg.exe, its in the bin folder).

## "Your code sucks"
i know, i dont have much experience with electron,
you're free to improve it and make a [pull request](https://github.com/REVENGE977/stremio-enhanced/pulls).


## Todo
- might switch to [stremio web v5](https://github.com/Stremio/stremio-web)
- updater
## How do I make my own plugin?
Plugins are simply javascript files running on the client-side, so just write your javascript code like you normally would on client-side
and add .plugin.js at the end of the javascript file name, and move your javascript plugin to the plugins folder (%appdata%\stremio-enhanced\plugins).

As of version v0.3 you are required to provide meta data for the plugin, here is an example:
```js
/**
* @name YourPluginNameHere
* @description What does your plugin do?
* @updateUrl https://raw.githubusercontent.com/REVENGE977/BetterEpisodeList/main/BetterEpisodeList.plugin.js
* @version 1.0.0
* @author AuthorName
*/
```
## How do I make my own theme?
You just take the stock stremio css file and modify it. The stock css file can be found [here](https://github.com/REVENGE977/stremio-enhanced-community/blob/main/examples/stockstremio_unminified.theme.css). You can also just take the default theme yourself, by opening devtools and going to the Source tab, and there you will find the css file for the default theme. You can take it and put it [here](https://www.unminify2.com/) to unminify it and make it easier to read and modify.

## Update v0.3
- Now relies on [Stremio Service](https://github.com/Stremio/stremio-service) to run (if stremio service isn't installed it will guide the user to install it). This is means you will get a similar streaming experience to the official app.
- Checks if the installed version is the latest version or not. Startup checking can be disabled from the settings (not tested yet).
- Made a new plugin called "BetterEpisodesList." The idea is to add a new season option in shows that says "all." When the option is chosen, the plugin will take all of the episodes available in a show (except specials) and put them in one list for you, numbered as they are in one list. This is very useful for shows like One Piece, Where in other platforms the episodes are listed as they are in one season. This plugin brings that to Stremio. The plugin also adds a search bar for the user to search episodes, which is a feature apparent in [Stremio Web](https://web.stremio.com/).
- Now shows the list of plugins/themes in more details. It will show the details provided in the meta data (the first few comment lines). You can check examples/BetterEpisodesList.plugin.js.
- The source is a bit more organized now.
- Fixed the flag for --devtools. Now if the user launches stremio-enhanced with the flag --devtools it will open the F12 devtools on launch properly.
- Added the hotkey Ctrl+Shift+I to open the devtools.
- Added the flag --no-stremio-service for users who don't want to use stremio service and override the streaming server URL from the settings.
- Now sets the background to black on startup, so you don't get flashbanged on launch.
*Note: I've only tested the update on Windows.*
192 changes: 192 additions & 0 deletions examples/BetterEpisodeList.plugin.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,192 @@
/**
* @name BetterEpisodeList
* @description Adds a search bar to search episodes either by name or number, and adds an option to show all episodes in one list.
* @updateUrl https://raw.githubusercontent.com/REVENGE977/BetterEpisodeList/main/BetterEpisodeList.plugin.js
* @version 1.0.0
* @author REVENGE977
*/

//regex pattern for shows and movies urls
const regexPattern = /\/detail\/(series|movie)\/[a-zA-Z0-9]+(?:\/[a-zA-Z0-9]+)?(?:\/tt[0-9]+%3A\d+:\d+)?(?:\/[^\/]+)?\/?$/;

window.addEventListener('popstate', () => {
console.log("[ BetterEpisodeList ] URL changed: " + window.location.href);
waitForElm('[name="season"]').then(() => {
if(regexPattern.test(window.location.href)) {
console.log("[ BetterEpisodeList ] regex matches!");
if(document.getElementById("episode-search-field")) document.getElementById("episode-search-field").remove();
if(document.getElementById("AllEpisodesPlugin")) document.getElementById("AllEpisodesPlugin").remove();

//insert episode search bar
addSearchBar();

//insert all option into the season selection
const seasonSelectMenu = document.getElementsByName("season")[0];
addAllOption(seasonSelectMenu);

seasonSelectMenu.addEventListener('change', (e) => {
let pluginAddedEpisodes = document.getElementsByName("allEpisodesPlugin-episode");

if (e.target.value === 'all') {
console.log('[ BetterEpisodeList ] Option All is selected!');
let injector = angular.injector(['ng']);
let compile = injector.get('$compile');
let container = document.getElementsByClassName('episodes-list')[0];
let scope = angular.element(container).scope()

scope.$apply(() => {
if(pluginAddedEpisodes.length > 0) {
pluginAddedEpisodes.forEach(element => {
if(element) element.style.display = "flex";
})
} else {
hideAddedEpisodes();
addEpisodesToAll(compile, scope);
}
});
} else if (e.target.value != 'all' && pluginAddedEpisodes.length > 0) {
console.log("[BetterEpisodeList] Hiding all episodes.")
pluginAddedEpisodes.forEach(element => {
if(element) element.style.display = "none";
})
}
});
}
})
});

function addSearchBar() {
let injector = angular.injector(['ng']);
let compile = injector.get('$compile');

let heading = document.querySelector(".episodes > .heading");
let headingScope = angular.element(heading).scope();

let inputElm = document.createElement('input');
inputElm.setAttribute("id", "episode-search-field");
inputElm.setAttribute("tabindex", "-1");
inputElm.setAttribute("placeholder", "Search episode by name or number");
inputElm.setAttribute("type", "text");
inputElm.setAttribute("class", "ng-pristine ng-valid ng-isolate-scope ng-empty ng-touched");
inputElm.setAttribute("style", `
width: -webkit-fill-available;
position: relative;
margin-top: 5%;`);

heading.appendChild(inputElm);
compile(inputElm)(headingScope);

inputElm.addEventListener("input", () => {
searchEpisodes(inputElm.value);
})
}

function addAllOption(seasonSelectMenu) {
let allOption = document.createElement('option');
allOption.value = 'all';
allOption.text = 'All';
allOption.id = "AllEpisodesPlugin";

seasonSelectMenu.insertBefore(allOption, seasonSelectMenu.firstChild);

return seasonSelectMenu;
}

function addEpisodesToAll(compile, scope) {
const container = document.getElementsByClassName('episodes-list')[0];
const episodes = scope.info.availableEpisodes || [];

let episodesCounter = 0;

episodes.forEach(episode => {
let isSpecialEpisode = episode.season == 0;
if(isSpecialEpisode) return;
episodesCounter++;

let childScope = scope.$new();

childScope.libItem = scope.item;
childScope.metaItem = scope.info;
childScope.intent = "player";
childScope.episode = episode;

let li = document.createElement('li');

li.setAttribute('ng-click', `open({ libItem: libItem, metaItem: metaItem, video: episode, intent: "player" })`);
li.setAttribute('tabindex', '-1');
li.setAttribute('title', `${episode.name}: Season ${episode.season}, Episode ${episode.number}, AllEpisode: ${episodesCounter}`);
li.setAttribute("ng-right-click", "!isUpcoming(episode) && contextMenuVideo(item, info, episode, $event)");
li.setAttribute("name", "allEpisodesPlugin-episode");

li.innerHTML = `
<div class="thumbnail">
<img stremio-image="::{ url: ${episode.thumbnail} }" data-image="${episode.thumbnail}" loading="lazy" src="${episode.thumbnail}">
</div>
<div class="episode-details">
<div class="title ng-binding">${episodesCounter}. ${episode.title}</div>
<div class="footer">
<div class="date ng-isolate-scope">${formatTimestamp(episode.released.getTime())}</div>
<div class="date ng-isolate-scope">Season ${episode.season}, Ep. ${episode.number}</div>
</div>
</div>`;

container.appendChild(li);
compile(li)(childScope);
});
}

function formatTimestamp(timestamp) {
try {
const date = new Date(timestamp);
const months = ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'];
const formattedDate = `${date.getDate()} ${months[date.getMonth()]} ${date.getFullYear()}`;
return formattedDate;
} catch {
return 'N/A';
}
}

function waitForElm(selector) {
return new Promise(resolve => {
if (document.querySelector(selector)) {
return resolve(document.querySelector(selector));
}

const observer = new MutationObserver(() => {
if (document.querySelector(selector)) {
observer.disconnect();
resolve(document.querySelector(selector));
}
});

observer.observe(document.body, {
childList: true,
subtree: true
});
});
}

function hideAddedEpisodes(){
const container = document.getElementsByClassName('episodes-list')[0];
var elements = container.children;

for (var i = 0; i < elements.length; i++) {
elements[i].style.display = 'none';
}
}

function searchEpisodes(query) {
let liElements = document.querySelectorAll('li');
let allEpisodes = Array.from(liElements).filter((liElement) => {
return liElement.querySelector('div.episode-details') !== null;
});

allEpisodes.forEach((episode) => {
let titleAttribute = episode.getAttribute('title').toLowerCase();
if (titleAttribute && titleAttribute.includes(query.toLowerCase())) {
episode.style.display = 'flex';
} else {
episode.style.display = 'none';
}
});
}
Loading

0 comments on commit ff3cb78

Please sign in to comment.