NOTICE: By continued use of this site you understand and agree to the binding Terms of Service and Privacy Policy.
// ==UserScript==
// @name VK Top Header Menu
// @namespace http://tampermonkey.net/
// @version 1.7
// @description Show top header menu in vk
// @author Flyink13
// @match https://*.vk.com/*
// @resource apiLib https://ifx.su/~va
// @grant GM_getResourceText
// @copyright 2019, flyink13 (https://openuserjs.org/users/flyink13)
// @updateURL https://openuserjs.org/meta/flyink13/VK_Top_Header_Menu.meta.js
// @license MIT
// ==/UserScript==
/* global gpeByClass, API, nav, showWiki, mentionOver, UiScroll, GM_getResourceText */
function TopHeaderMenu() {
var styles = `
.top_header_menu {
height: 42px;
line-height: 42px;
cursor: pointer;
color: #fff;
float: left;
}
.top_header_menu_wrap {
position: absolute;
line-height: normal;
cursor: default;
visibility: hidden;
opacity: 0;
top: 52px;
right: -1px;
background: #fff;
color: #000;
border: 1px solid #c5d0db;
border-top: none;
border-radius: 0 0 4px 4px;
box-shadow: 0 20px 40px 0 rgba(0,0,0,.3);
transition: opacity 100ms linear, top 100ms linear, visibility 100ms linear;
}
.top_header_menu.active .top_header_menu_wrap {
visibility: visible;
opacity: 1;
filter: none;
top: 42px;
}
.top_header_menu:before {
content: '';
width: 6px;
font-size: 7px;
height: 6px;
color: #1d3c5f;
background: #1d3c5f;
display: inline-block;
box-shadow: -1em 0em, -1em -1em, 0em -1em;
margin: -0.25em 24px;
}
.top_header_menu.active:before {
color: #fff;
background: #fff;
}
.top_header_menu_wrap:before {
position: absolute;
pointer-events: none;
border: solid transparent;
content: '';
height: 0;
width: 0;
right: 23px;
top: -10px;
}
.top_header_menu_wrap:before {
border-width: 5px;
margin: 0 -5px;
border-bottom-color: #fff;
}
.top_header_menu_content {
overflow: auto;
width: 318px;
height: 250px;
}
.top_header_menu_content {
align-items: center;
}
.top_header_menu_content .ui_scroll_content {
padding: 12px;
}
.top_header_menu_content .top_header_link {
width: 74px;
display: inline-block;
overflow: hidden;
margin: 2px;
margin-bottom: 0px;
padding: 10px;
border-radius: 3px;
color: #2a5885;
cursor: pointer;
text-align: center;
}
.top_header_menu_content a {
text-decoration: none;
}
.top_header_menu_content .top_header_link:hover {
box-shadow: 0 0 1px #4a75a7;
}
.top_header_menu_content .top_header_icon {
width: 50px;
height: 50px;
border-radius: 100%;
margin-bottom: 6px;
display: inline-block;
background-position: center;
position: relative;
background-size: cover;
}
.top_header_menu_content .top_header_name {
white-space: nowrap;
text-overflow: ellipsis;
overflow: hidden;
display: block;
}
.top_header_menu input {
box-shadow: 0px 1px 0px #e7e8ec;
font-size: 13px;
}
.top_header_icon_counter[title]:after {
content: attr(title);
background: #d1d9e0;
padding: 5px;
position: absolute;
bottom: 0px;
right: 0px;
border-radius: 3px;
margin: -3px;
font-size: 11px;
text-align: center;
}
.top_header_menu.line_view .top_header_menu_content {
padding: 0px;
}
.top_header_menu.line_view .top_header_icon {
width: 32px;
height: 32px;
float: left;
margin-right: 8px;
margin-bottom: 0px;
}
.top_header_menu.line_view .top_header_name {
line-height: 32px;
}
.top_header_menu.line_view .top_header_link {
padding: 8px 12px;
display: block;
width: 100%;
text-align: left;
box-sizing: border-box;
margin: 0px;
margin-bottom: 1px;
border-radius: 0px;
}
.top_header_menu.line_view .top_header_menu_content .top_header_link:hover {
box-shadow: none;
background: #eee;
}
`;
var code = `
var user_ids = API.fave.getUsers({ }).items@.id;
return {
app: API.apps.getFromMenu({ filter: 'vk_apps' }).favorites,
link: API.fave.get({ item_type: 'link' }).items,
group: API.fave.getPages({ type: 'groups' }).items +
API.groups.get({ filter: 'admin', extended: 1, fields: 'can_message,is_admin' }).items,
user: API.users.get({ user_ids: user_ids, fields: 'photo_100,photo_200' }),
};`;
var linksNames = {
'https://vk.com/im': 'Сообщения'
};
var TopLn = document.getElementById('top_profile_link');
var MenuB = document.createElement('div');
var MenuW = document.createElement('div');
var MenuC = document.createElement('div');
var MenuS = document.createElement('input');
var StyEl = document.createElement('style');
if (!TopLn) return;
MenuS.placeholder = 'Поиск';
MenuS.autocomplete = 'off';
MenuS.spellcheck = 'off';
StyEl.innerHTML = styles;
MenuB.className = 'top_header_menu top_nav_btn head_nav_item fl_r';
MenuW.className = 'top_header_menu_wrap';
MenuC.className = 'top_header_menu_content';
MenuS.className = 'ui_search_field _field';
function updateCounter(el, timeLimit) {
if (!/top_header_icon_counter/.test(el.firstChild.className)) {
return;
}
if (Date.now() - el.lastUpdate < timeLimit) {
return;
}
el.lastUpdate = Date.now();
var group_id = el.href.match(/\d+/)[0];
API('messages.getConversations', {
filter: 'unread',
group_id: group_id,
}).then((r) => {
var count = r.response.count;
if (count) {
el.firstChild.title = count;
} else {
delete el.firstChild.title;
}
});
}
function getMenuItems() {
return Array.from(MenuC.querySelectorAll('.top_header_link'));
}
function updateCounters() {
getMenuItems().forEach((el) => {
updateCounter(el, 30e3);
});
}
function search() {
var reg = new RegExp(MenuS.value, 'i');
getMenuItems().forEach((el) => {
if (MenuS.value === '' || reg.test(el.textContent)) {
el.style.display = '';
} else {
el.style.display = 'none';
}
});
}
MenuS.onkeyup = search;
MenuS.onchange = search;
document.body.addEventListener('mousedown', (e) => {
var el = e.target.firstChild || e.target;
var toMenu = gpeByClass('top_header_menu', el);
var toWrap = gpeByClass('top_header_menu_wrap', el);
if (toWrap) return;
if (toMenu) {
if (!MenuB.classList.contains('active')) {
MenuS.value = '';
search();
updateCounters();
if (MenuC._scroll) {
MenuC._scroll.scrollTop(0);
}
}
MenuB.classList.toggle('active');
setTimeout(() => MenuS.focus(), 100);
return;
}
MenuB.classList.remove('active');
});
MenuB.appendChild(MenuW);
MenuW.appendChild(MenuS);
MenuW.appendChild(MenuC);
MenuB.appendChild(StyEl);
API('execute', {code, v: '5.98'}).then((res) => {
var app_ids = [];
var favs = res.response;
var appsEls = [].map.call(document.querySelectorAll('.genre_app a'), (link) => {
var app_id = 1 * link.href.match(/\d+/)[0];
app_ids.push(app_id);
});
if (!appsEls || !appsEls.length) {
return favs;
}
return API('apps.get', {
app_ids,
extended: 1
}).then((res) => {
var webApps = res.response.items;
favs.app = favs.app.concat(webApps);
return favs;
});
}).then((favs) => {
console.log(favs);
var df = document.createDocumentFragment();
Object.keys(favs).forEach((type) => {
favs[type].forEach((fav) => {
var favWrap = document.createElement('a');
var favImg = document.createElement('div');
var favName = document.createElement('a');
favName.className = 'top_header_name';
favWrap.className = 'top_header_link';
favImg.className = 'top_header_icon';
favWrap.onclick = () => {
MenuB.classList.remove('active');
return nav.go(favWrap.href);
};
favImg.onmouseover = () => updateCounter(favWrap, 10e3);
switch (type) {
case 'app':
favImg.src = fav.icon_150 || '/images/vkapp_d.png';
favName.textContent = fav.title;
favWrap.href = '/app' + fav.id;
favWrap.onclick = () => {
MenuB.classList.remove('active');
return showWiki({
w: 'app' + fav.id
});
};
break;
case 'group':
Object.assign(fav, fav.group || {});
favWrap.href = '/club' + fav.id;
favName.textContent = fav.name;
favImg.src = fav.photo_200 || '/images/camera_200.png';
favName.setAttribute('mention_id', 'club' + fav.id);
favName.onmouseover = (e) => mentionOver(favName, {shift: [20, 7, 7]});
if (fav.can_message && fav.is_admin) {
favImg.className += ' top_header_icon_counter';
}
break;
case 'user':
favWrap.href = '/id' + fav.id;
favName.textContent = fav.first_name + ' ' + fav.last_name;
favImg.src = fav.photo_200 || fav.photo_100 || '/images/camera_200.png';
favName.setAttribute('mention_id', 'id' + fav.id);
favName.onmouseover = (e) => mentionOver(favName, {shift: [20, 7, 7]});
break;
case 'link':
Object.assign(fav, fav.link);
favWrap.href = fav.url;
favImg.src = fav.photo ? fav.photo.sizes[0].url : '/images/camera_200.png?ava=1';
favName.textContent = linksNames[fav.title] || fav.title;
break;
}
favImg.style.backgroundImage = 'url(' + favImg.src + ')';
favWrap.appendChild(favImg);
favWrap.appendChild(favName);
df.appendChild(favWrap);
});
});
MenuC.appendChild(df);
}).catch((e) => {
console.error(e);
MenuC.textContent = 'Ошибка загрузки страницы';
}).then(() => {
TopLn.parentNode.insertBefore(MenuB, TopLn);
MenuC._scroll = new UiScroll(MenuC, {
shadows: true,
global: true,
});
});
}
(function injectScript() {
var script = document.createElement('script');
var code = '';
code += '(function(){' + (GM_getResourceText('apiLib')) + '})();';
code += '(' + TopHeaderMenu + ')();';
script.appendChild(document.createTextNode(code));
(document.body || document.head || document.documentElement).appendChild(script);
})();