Greasy Fork is available in English.

Exo Client

AI-powered automation sidebar + stealth adblock + 4K enforcer

이 스크립트를 설치하려면 Tampermonkey, Greasemonkey 또는 Violentmonkey와 같은 확장 프로그램이 필요합니다.

이 스크립트를 설치하려면 Tampermonkey와 같은 확장 프로그램을 설치해야 합니다.

이 스크립트를 설치하려면 Tampermonkey 또는 Violentmonkey와 같은 확장 프로그램이 필요합니다.

이 스크립트를 설치하려면 Tampermonkey 또는 Userscripts와 같은 확장 프로그램이 필요합니다.

이 스크립트를 설치하려면 Tampermonkey와 같은 확장 프로그램이 필요합니다.

이 스크립트를 설치하려면 유저 스크립트 관리자 확장 프로그램이 필요합니다.

(이미 유저 스크립트 관리자가 설치되어 있습니다. 설치를 진행합니다!)

이 스타일을 설치하려면 Stylus와 같은 확장 프로그램이 필요합니다.

이 스타일을 설치하려면 Stylus와 같은 확장 프로그램이 필요합니다.

이 스타일을 설치하려면 Stylus와 같은 확장 프로그램이 필요합니다.

이 스타일을 설치하려면 유저 스타일 관리자 확장 프로그램이 필요합니다.

이 스타일을 설치하려면 유저 스타일 관리자 확장 프로그램이 필요합니다.

이 스타일을 설치하려면 유저 스타일 관리자 확장 프로그램이 필요합니다.

(이미 유저 스타일 관리자가 설치되어 있습니다. 설치를 진행합니다!)

// ==UserScript==
// @name         Exo Client
// @namespace    exo.client
// @version      1.0
// @description  AI-powered automation sidebar + stealth adblock + 4K enforcer
// @match        *://*/*
// @grant        GM_addStyle
// @grant        GM_xmlhttpRequest
// @connect      *
// ==/UserScript==

(function() {
'use strict';

/* ---------------- CONFIG ---------------- */
const CONFIG = {
    AI_ENDPOINT: "https://openrouter.ai/api/v1/chat/completions", // change if needed
    API_KEY: "PUT_KEY_HERE",
};

/* ---------------- UI ---------------- */
const btn = document.createElement('div');
btn.id = 'exo-btn';
btn.innerHTML = '✦';
document.body.appendChild(btn);

const sidebar = document.createElement('div');
sidebar.id = 'exo-sidebar';
sidebar.innerHTML = `
<div id="exo-header">Exo Client</div>
<div id="exo-chat"></div>
<div id="exo-input-wrap">
<input id="exo-input" placeholder="Ask Exo to do anything…" />
</div>`;
document.body.appendChild(sidebar);

GM_addStyle(`
#exo-btn {
 position: fixed;
 bottom: 20px;
 right: 20px;
 width: 50px;
 height: 50px;
 background: rgba(255,255,255,0.1);
 backdrop-filter: blur(10px);
 border-radius: 50%;
 display:flex;
 align-items:center;
 justify-content:center;
 font-size:20px;
 cursor:pointer;
 z-index:999999;
}

#exo-sidebar {
 position: fixed;
 top:0;
 right:-400px;
 width:400px;
 height:100%;
 background: rgba(20,20,20,0.85);
 backdrop-filter: blur(20px);
 color:white;
 transition: right 0.3s ease;
 display:flex;
 flex-direction:column;
 z-index:999998;
 font-family: 'Product Sans', sans-serif;
}

#exo-sidebar.open { right:0; }

#exo-header {
 padding:15px;
 font-size:18px;
 border-bottom:1px solid rgba(255,255,255,0.1);
}

#exo-chat {
 flex:1;
 overflow:auto;
 padding:10px;
}

#exo-input-wrap {
 padding:10px;
 border-top:1px solid rgba(255,255,255,0.1);
}

#exo-input {
 width:100%;
 padding:10px;
 border:none;
 outline:none;
 border-radius:10px;
}
`);

btn.onclick = () => sidebar.classList.toggle('open');

document.addEventListener('keydown', e => {
 if(e.ctrlKey && e.shiftKey && e.key.toLowerCase()==='x'){
  sidebar.classList.toggle('open');
 }
});

/* ---------------- AI ---------------- */
const input = document.getElementById('exo-input');
const chat = document.getElementById('exo-chat');

input.addEventListener('keydown', async e => {
 if(e.key === 'Enter'){
  const msg = input.value;
  input.value = '';
  addMsg('user', msg);

  const res = await fetch(CONFIG.AI_ENDPOINT, {
    method:'POST',
    headers:{
      'Authorization': 'Bearer ' + CONFIG.API_KEY,
      'Content-Type':'application/json'
    },
    body: JSON.stringify({
      model: 'openai/gpt-4o-mini',
      messages:[{role:'user',content:msg}]
    })
  });

  const data = await res.json();
  const reply = data.choices?.[0]?.message?.content || 'No response';

  addMsg('ai', reply);
  runAutomation(reply);
 }
});

function addMsg(role, text){
 const div = document.createElement('div');
 div.textContent = text;
 div.style.margin = '8px 0';
 div.style.opacity = role==='ai'?0.8:1;
 chat.appendChild(div);
 chat.scrollTop = chat.scrollHeight;
}

/* ---------------- AUTOMATION ENGINE ---------------- */
function runAutomation(code){
 try{
  new Function(code)();
 }catch(e){
  console.error('Automation error', e);
 }
}

/* ---------------- 4K ENFORCER ---------------- */
function forceQuality(){
 document.querySelectorAll('video').forEach(v => {
  v.setAttribute('playsinline','');
  v.setAttribute('webkit-playsinline','');
  v.playbackRate = 1;
 });
}
setInterval(forceQuality, 2000);

/* ---------------- STEALTH ADBLOCK ---------------- */
const origFetch = window.fetch;
window.fetch = async (...args) => {
 const url = args[0];
 if(typeof url === 'string' && url.includes('ads')){
  return new Response('', {status:200});
 }
 return origFetch(...args);
};

const observer = new MutationObserver(muts => {
 muts.forEach(m => {
  m.addedNodes.forEach(n => {
    if(n.tagName==='IFRAME' || n.tagName==='VIDEO'){
      if(n.src && n.src.includes('ads')) n.remove();
    }
  });
 });
});

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

})();