const { getCardColors, FlexLayout, clampValue } = require("../src/utils"); const createProgressNode = ({ width, color, name, progress }) => { const paddingRight = 95; const progressTextX = width - paddingRight + 10; const progressWidth = width - paddingRight; const progressPercentage = clampValue(progress, 2, 100); return ` ${name} ${progress}% `; }; const lowercaseTrim = (name) => name.toLowerCase().trim(); const renderTopLanguages = (topLangs, options = {}) => { const { hide_title, card_width, title_color, text_color, bg_color, hide, theme, } = options; let langs = Object.values(topLangs); let langsToHide = {}; // populate langsToHide map for quick lookup // while filtering out if (hide) { hide.forEach((langName) => { langsToHide[lowercaseTrim(langName)] = true; }); } // filter out langauges to be hidden langs = langs .sort((a, b) => b.size - a.size) .filter((lang) => { return !langsToHide[lowercaseTrim(lang.name)]; }); const totalSize = langs.reduce((acc, curr) => { return acc + curr.size; }, 0); // returns theme based colors with proper overrides and defaults const { titleColor, textColor, bgColor } = getCardColors({ title_color, text_color, bg_color, theme, }); const width = isNaN(card_width) ? 300 : card_width; let height = 45 + (langs.length + 1) * 40; if (hide_title) { height -= 30; } return ` ${ hide_title ? "" : `Top Languages` } ${FlexLayout({ items: langs.map((lang) => { return createProgressNode({ width: width, name: lang.name, color: lang.color || "#858585", progress: ((lang.size / totalSize) * 100).toFixed(2), }); }), gap: 40, direction: "column", }).join("")} `; }; module.exports = renderTopLanguages;