- // ==UserScript==
- // @name Steam Inventory Items Table
- // @namespace https://github.com/Kostya12rus/steam_inventory_stack/
- // @supportURL https://github.com/Kostya12rus/steam_inventory_stack/issues
- // @version 1.0.1
- // @description Shows you all your items in a cool way.
- // @author Kostya12rus
- // @match https://steamcommunity.com/profiles/*/inventory*
- // @match https://steamcommunity.com/id/*/inventory*
- // @license AGPL-3.0
- // ==/UserScript==
-
- class MarketDescription {
- constructor(descriptionDict = {}) {
- this.type = descriptionDict.type || '';
- this.value = descriptionDict.value || '';
- }
- }
- class MarketAssetDescription {
- constructor(assetDescriptionDict = {}) {
- this.appid = assetDescriptionDict.appid || 0;
- this.classid = assetDescriptionDict.classid || '';
- this.instanceid = assetDescriptionDict.instanceid || '';
- this.name = assetDescriptionDict.name || '';
- this.nameColor = assetDescriptionDict.name_color || '';
- this.marketName = assetDescriptionDict.market_name || '';
- this.marketHashName = assetDescriptionDict.market_hash_name || '';
-
- this.tradable = Boolean(assetDescriptionDict.tradable || false);
- this.marketable = Boolean(assetDescriptionDict.marketable || false);
- this.commodity = Boolean(assetDescriptionDict.commodity || false);
-
- this.marketTradableRestriction = assetDescriptionDict.market_tradable_restriction || -1;
- this.marketMarketableRestriction = assetDescriptionDict.market_marketable_restriction || -1;
-
- this.iconUrl = assetDescriptionDict.icon_url || '';
- this.iconUrlLarge = assetDescriptionDict.icon_url_large || '';
-
- this.currency = assetDescriptionDict.currency || 0;
- this.descriptions = (assetDescriptionDict.descriptions || []).map(d => new MarketDescription(d));
- this.type = assetDescriptionDict.type || '';
- this.backgroundColor = assetDescriptionDict.background_color || '';
- }
- }
- class MarketItem {
- constructor(itemDict = {}) {
- this.name = itemDict.name || ' ';
- this.hashName = itemDict.hash_name || '';
-
- this.sellListings = itemDict.sell_listings || 0;
- this.sellPrice = itemDict.sell_price || 0;
- this.sellPriceText = itemDict.sell_price_text || '';
- this.salePriceText = itemDict.sale_price_text || '';
-
- this.assetDescription = new MarketAssetDescription(itemDict.asset_description || {});
-
- this.appName = itemDict.app_name || '';
- this.appIcon = itemDict.app_icon || '';
- }
-
- loadSave(data) {
- this.name = data.name || ' ';
- this.hashName = data.hashName || '';
-
- this.sellListings = data.sellListings || 0;
- this.sellPrice = data.sellPrice || 0;
- this.sellPriceText = data.sellPriceText || '';
- this.salePriceText = data.salePriceText || '';
-
- this.assetDescription = new MarketAssetDescription(data.assetDescription || {});
-
- this.appName = data.appName || '';
- this.appName = data.appName || '';
- return this;
- }
-
- toString() {
- return `<${this.constructor.name}> name: ${this.name}, price: ${this.sellPriceText}, listings: ${this.sellPrice}`;
- }
-
- isBugItem() {
- return this.hashName !== this.assetDescription.marketHashName;
- }
-
- isEmpty() {
- return this.hashName === '';
- }
-
- iconUrl() {
- if (!this.assetDescription.iconUrl) return '';
- return `https://community.akamai.steamstatic.com/economy/image/${this.assetDescription.iconUrl}/330x192?allow_animated=1`;
- }
-
- marketUrl() {
- if (!this.assetDescription.appid || !this.assetDescription.marketHashName) return '';
- return `https://steamcommunity.com/market/listings/${this.assetDescription.appid}/${this.assetDescription.marketHashName}`;
- }
-
- marketHashName() {
- return this.assetDescription.marketHashName;
- }
-
- color() {
- return this.assetDescription.nameColor ? `#${this.assetDescription.nameColor}`.replace('##', '#') : '';
- }
-
- isCurrentGame(appId) {
- return String(this.assetDescription.appid) === String(appId);
- }
-
- replaceNumberInCurrency(newNumber) {
- return this.sellPriceText.replace(/\d{1,3}(?:\s?\d{3})*(?:[,.]\d+)?/, newNumber);
- }
-
- generateNumberInCurrency(newNumber) {
- return this.replaceNumberInCurrency((newNumber / 100).toFixed(2));
- }
-
- multiplyPriceInCurrency(count) {
- return this.generateNumberInCurrency(this.sellPrice * count);
- }
-
- calculateCommission(price = null) {
- return this.generateNumberInCurrency(this.calculateCommissionInteger(price));
- }
-
- calculateCommissionInteger(price = null) {
- if (!price) price = this.sellPrice;
- const commission = Math.abs(price - (price / 115 * 100));
- return price - commission;
- }
- }
-
- class InventoryDescription {
- constructor(descriptionDict = {}) {
- this.type = descriptionDict.type || '';
- this.value = descriptionDict.value || '';
- }
- }
- class InventoryTag {
- constructor(tagDict = {}) {
- this.category = tagDict.category || '';
- this.internalName = tagDict.internal_name || '';
- this.categoryName = tagDict.category_name || '';
- this.name = tagDict.name || '';
- }
- }
- class InventoryItem {
- constructor(itemDict = {}) {
- this.classid = itemDict.classid || '';
- this.instanceid = itemDict.instanceid || '';
- this.amount = itemDict.amount || '1';
-
- const rgDescriptions = itemDict.rgDescriptions || {};
- this.rgDescriptions = {
- appid: rgDescriptions.appid || '',
- classid: rgDescriptions.classid || '',
- instanceid: rgDescriptions.instanceid || '',
- iconUrl: rgDescriptions.icon_url || '',
- iconUrlLarge: rgDescriptions.icon_url_large || '',
- iconDragUrl: rgDescriptions.icon_drag_url || '',
- name: rgDescriptions.name || '',
- marketHashName: rgDescriptions.market_hash_name || '',
- marketName: rgDescriptions.market_name || '',
- nameColor: rgDescriptions.name_color || '',
- backgroundColor: rgDescriptions.background_color || '',
- type: rgDescriptions.type || '',
- tradable: Boolean(rgDescriptions.tradable || false),
- marketable: Boolean(rgDescriptions.marketable || false),
- commodity: Boolean(rgDescriptions.commodity || false),
- marketTradableRestriction: rgDescriptions.market_tradable_restriction || '-1',
- marketMarketableRestriction: rgDescriptions.market_marketable_restriction || '7',
- descriptions: (rgDescriptions.descriptions || []).map(desc => new InventoryDescription(desc)),
- tags: (rgDescriptions.tags || []).map(tag => new InventoryTag(tag))
- };
- }
-
- updateRgDescriptions(rgDescriptions) {
- this.rgDescriptions = {
- appid: rgDescriptions.appid || '',
- classid: rgDescriptions.classid || '',
- instanceid: rgDescriptions.instanceid || '',
- iconUrl: rgDescriptions.icon_url || '',
- iconUrlLarge: rgDescriptions.icon_url_large || '',
- iconDragUrl: rgDescriptions.icon_drag_url || '',
- name: rgDescriptions.name || '',
- marketHashName: rgDescriptions.market_hash_name || '',
- marketName: rgDescriptions.market_name || '',
- nameColor: rgDescriptions.name_color || '',
- backgroundColor: rgDescriptions.background_color || '',
- type: rgDescriptions.type || '',
- tradable: Boolean(rgDescriptions.tradable || false),
- marketable: Boolean(rgDescriptions.marketable || false),
- commodity: Boolean(rgDescriptions.commodity || false),
- marketTradableRestriction: rgDescriptions.market_tradable_restriction || '-1',
- marketMarketableRestriction: rgDescriptions.market_marketable_restriction || '7',
- descriptions: (rgDescriptions.descriptions || []).map(desc => new InventoryDescription(desc)),
- tags: (rgDescriptions.tags || []).map(tag => new InventoryTag(tag))
- };
- }
-
- name() {
- if (!this.rgDescriptions.name) return '';
- return this.rgDescriptions.name;
- }
-
- iconUrl() {
- if (!this.rgDescriptions.iconUrl) return '';
- return `https://community.akamai.steamstatic.com/economy/image/${this.rgDescriptions.iconUrl}/330x192?allow_animated=1`;
- }
-
- marketUrl() {
- if (!this.rgDescriptions.appid || !this.rgDescriptions.marketHashName) return '';
- return `https://steamcommunity.com/market/listings/${this.rgDescriptions.appid}/${this.rgDescriptions.marketHashName}`;
- }
-
- color() {
- return this.rgDescriptions.nameColor ? `#${this.rgDescriptions.nameColor}`.replace('##', '#') : '';
- }
- }
- class InventoryManager {
- constructor(items = {}) {
- this.rgDescriptions = items.descriptions || {};
- if (typeof this.rgDescriptions !== 'object') {
- this.rgDescriptions = {};
- }
- this.rgInventory = items.assets || [];
- if (typeof this.rgInventory !== 'object') {
- this.rgInventory = [];
- }
- this.success = Boolean(items.success || false);
- this.inventory = [];
-
- this.parseInventory();
- }
-
- loadSaveInventory(oldData) {
- this.rgDescriptions = oldData.rgDescriptions || {};
- this.rgInventory = oldData.rgInventory || [];
- this.inventory = oldData.inventory || [];
- this.parseInventory();
- return this;
- }
-
- addNextInvent(nextInventory) {
- if (!(nextInventory instanceof InventoryManager)) return;
- this.rgInventory.push(...nextInventory.rgInventory);
- for (const [key, value] of Object.entries(nextInventory.rgDescriptions)) {
- this.rgDescriptions[key] = value;
- }
- this.parseInventory();
- }
-
- parseInventory() {
- this.inventory = [];
-
- for (const [key, item] of Object.entries(this.rgInventory)) {
- const inventoryItem = new InventoryItem(item);
- this.inventory.push(inventoryItem);
- }
-
- for (const item of this.inventory) {
- const classid = item.classid || 0;
- if (classid === 0) continue;
-
- const instanceid = item.instanceid || 0;
- for (const [key, itemDescription] of Object.entries(this.rgDescriptions)) {
- const classidD = itemDescription.classid || 0;
- if (classid !== classidD) continue;
-
- const instanceidD = itemDescription.instanceid || 0;
- if (instanceid !== instanceidD) continue;
-
- item.updateRgDescriptions(itemDescription);
- break;
- }
- }
- }
- }
-
- class TotalItem {
- constructor(classid) {
- this.classid = classid;
- this.items = [];
- this.marketData = null
- }
- addItem(item) {
- this.items.push(item);
- }
- setMarketData(marketData) {
- this.marketData = marketData;
- }
-
- getCount() {
- return this.items.reduce((total, _item) => total + parseInt(_item.amount), 0);
- }
- getConsolePrice(){
- if (!this.marketData) return 0;
- return this.marketData.sellPrice * this.getCount();
- }
- getConsolePriceOne(){
- if (!this.marketData) return 0;
- return this.marketData.sellPrice;
- }
- getOtherPrice(price = 0){
- if (!this.marketData) return null;
- return this.marketData.generateNumberInCurrency(price);
- }
- getPrice() {
- if (!this.marketData) return '';
- return this.marketData.multiplyPriceInCurrency(this.getCount());
- }
- getOnePrice() {
- if (!this.marketData) return '';
- return this.marketData.multiplyPriceInCurrency(1);
- }
- getIconUrl() {
- if (this.marketData)
- {
- return this.marketData.iconUrl();
- }
- else
- {
- const item = this.items[0];
- if (item)
- {
- return item.iconUrl();
- }
- }
- return '';
- }
- getMarketUrl() {
- if (this.marketData)
- {
- return this.marketData.marketUrl();
- }
- else
- {
- const item = this.items[0];
- if (item)
- {
- return item.marketUrl();
- }
- }
- return '';
- }
- getName() {
- if (this.marketData)
- {
- return this.marketData.name;
- }
- else
- {
- const item = this.items[0];
- if (item)
- {
- return item.name();
- }
- }
- return '';
- }
- getColor() {
- if (this.marketData)
- {
- return this.marketData.color();
- }
- else
- {
- const item = this.items[0];
- if (item)
- {
- return item.color();
- }
- }
- return '';
- }
- }
- class TotalItemsManager {
- constructor() {
- this.items = {};
- this.inventoryManager = new InventoryManager();
- this.marketItems = [];
- this.cachedData = {};
- }
- async loadTotalItems() {
- const { m_appid, m_contextid, m_steamid } = g_ActiveInventory;
-
- this.appid = m_appid;
- this.contextid = m_contextid;
- this.steamid = m_steamid;
-
- if (!this.cachedData) { this.cachedData = {}; }
-
- const cacheKey = `inventory_${this.steamid}_${this.appid}`;
- const now = new Date().getTime();
-
- if (this.cachedData[cacheKey] && this.cachedData[cacheKey].expiry > now) {
- this.inventoryManager = this.cachedData[cacheKey].inventoryManager;
- this.marketItems = this.cachedData[cacheKey].marketItems;
- this.parseItems();
- return;
- }
-
- this.inventoryManager = await this.getFullInventory();
- this.marketItems = await this.getGameMarketList();
- this.parseItems();
-
- if (!this.cachedData[cacheKey]) { this.cachedData[cacheKey] = {}; }
-
- this.cachedData[cacheKey].inventoryManager = this.inventoryManager;
- this.cachedData[cacheKey].marketItems = this.marketItems;
- this.cachedData[cacheKey].expiry = now + 10 * 60 * 1000;
- }
- parseItems() {
- this.items = [];
- for (const item of this.inventoryManager.inventory) {
- const classid = item.classid || 0;
- if (!this.items[classid]) {
- this.items[classid] = new TotalItem(classid);
- }
- this.items[classid].addItem(item);
- }
- for (const item of this.marketItems) {
- const classid = item.assetDescription.classid || 0;
- if (!this.items[classid]) {
- continue;
- }
- this.items[classid].setMarketData(item);
- }
- }
-
- async getGameMarketList(start = 0, count = 100) {
- const searchParams = new URLSearchParams({
- start: start,
- count: count,
- search_descriptions: 0,
- sort_column: 'popular',
- sort_dir: 'desc',
- appid: this.appid,
- norender: 1
- });
-
- const searchUrl = `https://steamcommunity.com/market/search/render/?${searchParams.toString()}`;
- let _marketItems = [];
-
- try {
- const marketResponse = await fetch(searchUrl, { method: 'GET', timeout: 10000 });
- if (marketResponse.ok) {
- const responseData = await marketResponse.json();
- if (responseData.success) {
- const items = responseData.results.map(itemData => new MarketItem(itemData));
- _marketItems = _marketItems.concat(items);
- const totalItemsAvailable = responseData.total_count || 0;
- if (totalItemsAvailable > start + count && start + count < 1000) {
- start += count;
- const additionalItems = await this.getGameMarketList(start, count);
- _marketItems = _marketItems.concat(additionalItems);
- }
- return _marketItems;
- }
- }
- } catch (e) {
- console.error(`getGameMarketList failed: ${e.message}`);
- }
- return _marketItems;
- }
- async getFullInventory() {
- try {
- const inventoryManager = new InventoryManager();
- return await this.getInventoryItems(inventoryManager);
- } catch (error) {
- console.error("Ошибка при получении предметов инвентаря:", error);
- }
- return this.inventoryManager;
- }
- getInventoryItems(inventoryManager, start_assetid = null) {
- const searchParams = new URLSearchParams({
- count: 2000,
- });
- if (start_assetid) {
- searchParams.set('start_assetid', start_assetid);
- }
- const url = `https://steamcommunity.com/inventory/${this.steamid}/${this.appid}/${this.contextid}?${searchParams.toString()}`;
- return fetch(url, {
- method: 'GET',
- headers: {
- 'Content-Type': 'application/json'
- }
- })
- .then(response => {
- if (!response.ok) {
- throw new Error(`HTTP error! status: ${response.status}`);
- }
- return response.json();
- })
- .then(data => {
- if (!data.success) {
- throw new Error("Не удалось получить данные инвентаря.");
- }
- inventoryManager.addNextInvent(new InventoryManager(data));
- const more_items = data.more_items;
- if (Number.isInteger(more_items) && more_items > 0) {
- return this.getInventoryItems(inventoryManager, data.last_assetid);
- }
- return inventoryManager;
- })
- .catch(error => {
- console.error("Ошибка проверки инвентаря:", error);
- throw error;
- });
- }
- }
-
- class ModalWindow {
- constructor(userNickname, userAvatar) {
- this.userNickname = userNickname
- this.userAvatar = userAvatar
- this.items = [];
-
- this.overlay = document.createElement('div');
- this.modal = document.createElement('div');
- this.closeButton = document.createElement('button');
-
- this.settingModal();
- }
-
- settingModal() {
- this.overlay.style.position = 'fixed';
- this.overlay.style.top = '0';
- this.overlay.style.left = '0';
- this.overlay.style.width = '100%';
- this.overlay.style.height = '100%';
- this.overlay.style.backgroundColor = 'rgba(0, 0, 0, 0.7)';
- this.overlay.style.zIndex = '9999';
- this.overlay.style.display = 'flex';
- this.overlay.style.justifyContent = 'center';
- this.overlay.style.alignItems = 'center';
- this.overlay.style.opacity = '0';
- this.overlay.style.transition = 'opacity 0.3s ease-in-out';
- this.overlay.addEventListener('click', this.closeModal.bind(this));
-
- this.modal.style.padding = '30px';
- this.modal.style.backgroundColor = '#242424';
- this.modal.style.borderRadius = '12px';
- this.modal.style.boxShadow = '0 8px 16px rgba(0, 0, 0, 0.5)';
- this.modal.style.color = '#e0e0e0';
- this.modal.style.width = '800px';
- this.modal.style.maxHeight = '90vh';
- this.modal.style.overflowY = 'auto';
- this.modal.style.position = 'relative';
- this.modal.style.transform = 'scale(0.9)';
- this.modal.style.opacity = '0';
- this.modal.style.transition = 'transform 0.3s ease-in-out, opacity 0.3s ease-in-out';
- this.modal.addEventListener('click', function(event) { event.stopPropagation(); });
-
- this.closeButton.innerText = '✖';
- this.closeButton.style.position = 'absolute';
- this.closeButton.style.top = '10px';
- this.closeButton.style.right = '10px';
- this.closeButton.style.background = 'none';
- this.closeButton.style.border = 'none';
- this.closeButton.style.color = '#fff';
- this.closeButton.style.fontSize = '20px';
- this.closeButton.style.cursor = 'pointer';
- this.closeButton.addEventListener('click', this.closeModal.bind(this));
-
- this.modal.appendChild(this.closeButton);
-
- this.addProfileInfo();
- this.addInventoryTable();
-
- this.overlay.appendChild(this.modal);
- document.body.appendChild(this.overlay);
-
- requestAnimationFrame(() => {
- this.overlay.style.opacity = '1';
- this.modal.style.transform = 'scale(1)';
- this.modal.style.opacity = '1';
- });
- }
- addProfileInfo() {
- this.profileContainer = document.createElement('div');
- this.profileContainer.style.display = 'flex';
- this.profileContainer.style.alignItems = 'center';
- this.profileContainer.style.justifyContent = 'center';
- this.profileContainer.style.marginBottom = '10px';
- this.profileContainer.style.color = '#ffffff';
-
- this.avatar = document.createElement('img');
- this.avatar.src = this.userAvatar;
- this.avatar.alt = 'Profile Avatar';
- this.avatar.style.width = '60px';
- this.avatar.style.height = '60px';
- this.avatar.style.borderRadius = '50%';
- this.avatar.style.marginRight = '15px';
-
- this.infoContainer = document.createElement('div');
- this.infoContainer.style.display = 'flex';
- this.infoContainer.style.alignItems = 'center';
-
- this.nickname = document.createElement('h2');
- this.nickname.innerText = this.userNickname;
- this.nickname.style.margin = '0 20px 0 0';
- this.nickname.style.fontSize = '20px';
- this.nickname.style.fontWeight = 'bold';
- this.nickname.style.color = '#6a5acd';
-
- this.detailsContainer = document.createElement('div');
- this.detailsContainer.style.display = 'flex';
- this.detailsContainer.style.alignItems = 'center';
-
- const itemCountContainer = document.createElement('div');
- itemCountContainer.style.marginRight = '20px';
- const itemCountLabel = document.createElement('p');
- itemCountLabel.innerText = 'Количество вещей';
- itemCountLabel.style.fontSize = '14px';
- itemCountLabel.style.color = '#b0c4de';
- itemCountLabel.style.margin = '0';
- itemCountLabel.style.textAlign = 'center';
- this.itemCountValue = document.createElement('p');
- this.itemCountValue.innerText = `123`;
- this.itemCountValue.style.margin = '0';
- this.itemCountValue.style.fontSize = '16px';
- this.itemCountValue.style.fontWeight = 'bold';
- this.itemCountValue.style.textAlign = 'center';
- this.itemCountValue.style.color = '#ffffff';
-
- itemCountContainer.appendChild(itemCountLabel);
- itemCountContainer.appendChild(this.itemCountValue);
-
- const inventoryValueContainer = document.createElement('div');
- const inventoryValueLabel = document.createElement('p');
- inventoryValueLabel.innerText = 'Сумма инвентаря';
- inventoryValueLabel.style.fontSize = '14px';
- inventoryValueLabel.style.color = '#b0c4de';
- inventoryValueLabel.style.margin = '0';
- inventoryValueLabel.style.textAlign = 'center';
- this.inventoryValue = document.createElement('p');
- this.inventoryValue.innerText = ``;
- this.inventoryValue.style.margin = '0';
- this.inventoryValue.style.fontSize = '16px';
- this.inventoryValue.style.fontWeight = 'bold';
- this.inventoryValue.style.textAlign = 'center';
- this.inventoryValue.style.color = '#ffffff';
-
- inventoryValueContainer.appendChild(inventoryValueLabel);
- inventoryValueContainer.appendChild(this.inventoryValue);
-
- this.detailsContainer.appendChild(itemCountContainer);
- this.detailsContainer.appendChild(inventoryValueContainer);
-
- this.infoContainer.appendChild(this.nickname);
- this.infoContainer.appendChild(this.detailsContainer);
-
- this.profileContainer.appendChild(this.avatar);
- this.profileContainer.appendChild(this.infoContainer);
-
- this.modal.appendChild(this.profileContainer);
- }
- addInventoryTable() {
- this.table = document.createElement('table');
- this.table.style.width = '100%';
- this.table.style.borderCollapse = 'separate';
- this.table.style.borderSpacing = '0';
- this.table.style.borderRadius = '8px';
- this.table.style.overflow = 'hidden';
- this.table.style.boxShadow = '0 4px 8px rgba(0,0,0,0.1)';
-
- const thead = document.createElement('thead');
- const headerRow = document.createElement('tr');
-
- const headers = [' ', 'Название предмета', 'Количество', 'Цена за штуку', 'Цена за все'];
- const textAligns = ['left', 'left', 'center', 'right', 'right'];
-
- headers.forEach((headerText, index) => {
- const th = document.createElement('th');
- th.innerText = headerText;
- th.style.borderBottom = '1px solid #ccc';
- th.style.textAlign = textAligns[index];
- th.style.cursor = 'pointer';
- th.setAttribute('data-order', 'asc');
- th.addEventListener('click', () => this.sortTableByColumn(index));
- headerRow.appendChild(th);
- });
-
- thead.appendChild(headerRow);
- this.table.appendChild(thead);
-
- this.tbody = document.createElement('tbody');
- this.table.appendChild(this.tbody);
-
- this.modal.appendChild(this.table);
- }
- sortTableByColumn(columnIndex) {
- const rows = Array.from(this.tbody.querySelectorAll('tr'));
- const isNumeric = columnIndex !== 1;
- const header = this.table.rows[0].cells[columnIndex];
-
- const order = header.getAttribute('data-order') === 'desc' ? 'asc' : 'desc';
- header.setAttribute('data-order', order);
-
- rows.sort((a, b) => {
- let aValue = a.cells[columnIndex].dataset.sort;
- let bValue = b.cells[columnIndex].dataset.sort;
-
- if (isNumeric) {
- aValue = parseFloat(aValue);
- bValue = parseFloat(bValue);
- }
-
- if (order === 'asc') {
- return aValue > bValue ? 1 : aValue < bValue ? -1 : 0;
- } else {
- return aValue < bValue ? 1 : aValue > bValue ? -1 : 0;
- }
- });
-
- while (this.tbody.firstChild) {
- this.tbody.removeChild(this.tbody.firstChild);
- }
-
- rows.forEach(row => this.tbody.appendChild(row));
- }
- addItemToTable(item) {
- const row = document.createElement('tr');
-
- const imgCell = document.createElement('td');
- const img = document.createElement('img');
- img.src = item.getIconUrl();
- img.alt = item.getName();
- img.style.height = '30px';
- img.style.width = 'auto';
- imgCell.appendChild(img);
- row.appendChild(imgCell);
-
- const nameCell = document.createElement('td');
- nameCell.style.color = item.getColor();
- nameCell.dataset.sort = item.getName();
-
- const nameLink = document.createElement('a');
- nameLink.href = item.getMarketUrl();
- nameLink.innerText = item.getName();
- nameLink.style.color = 'inherit';
- nameLink.style.textDecoration = 'none';
- nameLink.target = "_blank";
- nameCell.appendChild(nameLink);
- row.appendChild(nameCell);
-
- const quantityCell = document.createElement('td');
- quantityCell.innerText = item.getCount();
- quantityCell.style.textAlign = 'center';
- quantityCell.dataset.sort = item.getCount();
- row.appendChild(quantityCell);
-
- const pricePerItemCell = document.createElement('td');
- pricePerItemCell.innerText = item.getOnePrice();
- pricePerItemCell.style.textAlign = 'right';
- pricePerItemCell.dataset.sort = item.getConsolePriceOne();
- row.appendChild(pricePerItemCell);
-
- const totalPriceCell = document.createElement('td');
- totalPriceCell.innerText = item.getPrice();
- totalPriceCell.style.textAlign = 'right';
- totalPriceCell.dataset.sort = item.getConsolePrice();
- row.appendChild(totalPriceCell);
-
- this.tbody.appendChild(row);
- }
-
- addItem(newItem) {
- if (!newItem || newItem.getName() === '') { return; }
-
- this.items.push(newItem);
- this.addItemToTable(newItem);
-
- const totalCount = this.items.reduce((total, item) => total + item.getCount(), 0);
- this.itemCountValue.innerText = `${totalCount}`;
-
- const totalPriceFloat = this.items.reduce((total, item) => total + item.getConsolePrice(), 0);
- const itemWithMarketData = this.items.find(_item => _item.marketData);
- if (itemWithMarketData) {
- this.inventoryValue.innerText = `${itemWithMarketData.getOtherPrice(totalPriceFloat)}`;
- }
- }
-
- closeModal() {
- this.overlay.style.opacity = '0';
- this.modal.style.transform = 'scale(0.9)';
- this.modal.style.opacity = '0';
-
- setTimeout(() => {
- document.body.removeChild(this.overlay);
- }, 300);
- }
- }
-
- (function() {
- 'use strict';
- const appInventoryManager = new TotalItemsManager();
- createButton();
-
- async function localAppData() {
- await appInventoryManager.loadTotalItems()
- if (Object.keys(appInventoryManager.items).length === 0) {
- alert('Не удалось получить список предметов. Пожалуйста, попробуйте позже');
- return;
- }
-
- const nickNameElement = document.querySelector('.profile_small_header_name > a');
- const avatarUrlElement = document.querySelector('.profile_small_header_avatar .playerAvatar > img');
-
- const nickName = nickNameElement ? nickNameElement.textContent.trim() : '';
- const avatarUrl = avatarUrlElement ? avatarUrlElement.src : '';
-
- const modalWindow = new ModalWindow(nickName, avatarUrl);
- const sortedItemsList = Object.entries(appInventoryManager.items)
- .sort(([keyA], [keyB]) => keyA - keyB)
- .map(([key, value]) => value);
-
- sortedItemsList.forEach(item => modalWindow.addItem(item));
-
- }
-
- function createButton() {
- const button = document.createElement("button");
- button.innerText = "All Items Table";
- button.classList.add("btn_darkblue_white_innerfade");
- button.style.width = "100%";
- button.style.height = "30px";
- button.style.lineHeight = "30px";
- button.style.fontSize = "15px";
- button.style.position = "relative";
- button.style.zIndex = "2";
-
- button.addEventListener("click", async function() {
- if (button.disabled) return;
- button.disabled = true;
- try { await localAppData(); }
- catch (error) { console.error(error); }
- button.disabled = false;
- });
- function updateButtonText() {
- const gameNameElement = document.querySelector('.name_game');
- if (gameNameElement) {
- button.disabled = true;
- let remainingTime = 5;
- const gameName = gameNameElement.textContent.trim();
-
- button.innerText = `All Items Table in ${gameName} (wait ${remainingTime} sec)`;
- const timer = setInterval(() => {
- if (gameName !== gameNameElement.textContent.trim()) {
- clearInterval(timer);
- return;
- }
-
- remainingTime--;
- button.innerText = `All Items Table in ${gameName} (wait ${remainingTime} sec)`;
-
- if (remainingTime <= 0) {
- clearInterval(timer);
- button.innerText = `All Items Table in ${gameName}`;
- button.disabled = false;
- }
- }, 1000);
- }
- }
- function waitForElement(selector) {
- return new Promise((resolve) => {
- const observer = new MutationObserver((mutations, observer) => {
- if (document.querySelector(selector)) {
- observer.disconnect();
- resolve(document.querySelector(selector));
- }
- });
- observer.observe(document.body, { childList: true, subtree: true });
- });
- }
- const observer = new MutationObserver((mutations) => {
- mutations.forEach((mutation) => {
- if (mutation.type === 'childList' || mutation.type === 'characterData') {
- updateButtonText();
- }
- });
- });
- waitForElement('.name_game').then((target) => {
- observer.observe(target, { childList: true, subtree: true, characterData: true });
- updateButtonText();
- });
- const referenceElement = document.querySelector('#tabcontent_inventory');
- if (referenceElement) {
- referenceElement.parentNode.insertBefore(button, referenceElement);
- updateButtonText();
- }
- }
- })();