function renderArticleCard(data,widths={'w1':'50%','w2':'50%'}){let article_card=`
${(data.format||data.type)||'Article'}
${data.deck_name||data.title} ${data.excerpt?`${data.excerpt}`:''}
${data.username}
- ${data.submit_date}
${data.deck_views||data.deck_views===0?data.deck_views.toLocaleString():data.views.toLocaleString()} ${data.comments}
`;return article_card;} function renderArticleListItem(data){let article_list_item=`
${data.title}
${data.username}
${data.views.toLocaleString()} ${data.comments} ${data.submit_date}
`;return article_list_item;} function renderGridDeckCards(container,decks,{mode,clearContainer=true,widths={w1:'50%',w2:'50%'}}={}){const ctr=jQuery(container);if(clearContainer===true){ctr.empty();} for(const deck of decks){const elem=jQuery('
'+ '
'+ '
'+ '
'+ '
'+ '
'+ '
'+ '
'+ '
'+ '
'+ '
'+ ''+ ''+ '
'+ ''+ '
'+ ''+ '
'+ ''+ '
'+ ' '+ ' '+ '
'+ '
'+ '
'+ '
'+ '
'+ '
'+ '
'+ '
').appendTo(ctr);const isTournament=deck.format.toLowerCase().includes('tournament meta decks');let coverCard='';if(deck.cover_card){coverCard=deck.cover_card;}else if(deck.main_deck){const maindeckarray=JSON.parse(deck.main_deck);coverCard=maindeckarray[0];} elem.find('a').attr('href','/deck/'+deck.pretty_url);elem.find('.deck_article-card').attr('title',deck.deck_name).attr('data-src','https://images.ygoprodeck.com/images/cards_cropped/'+coverCard+'.jpg');elem.find('.deck_article-card-title').text(deck.deck_name);if(mode==='tournament'||isTournament){elem.find('.deck_article-card-overlay').children().first().children().eq(1).remove();if(deck.tournamentName){elem.find('.deck-type-badge').text(deck.tournamentName);elem.find('.deck_article-card-excerpt').remove();elem.find('.deck_article-avatar').remove();elem.find('.deck_article-card-stats').removeClass('d-flex flex-wrap flex-grow-1');const placement=' '+deck.tournamentPlacement;const playerCount='('+(deck.tournamentPlayerCountIsApproximate?'~':'')+deck.tournamentPlayerCount+' players)';const tournamentDate=' '+deck.submit_date;elem.find('.deck_article-card-stats').html(placement+' '+playerCount+' '+tournamentDate);if(deck.tournamentPlayerName){elem.find('.deck_article-card-stats').append(' piloted by '+deck.tournamentPlayerName);}}else{elem.find('.deck-type-badge').parent().remove();elem.find('.deck_article-card-excerpt').text(deck.deck_excerpt);elem.find('.deck_article-card-details').children('div').remove();}}else{elem.find('.deck-type-badge').text(deck.format);elem.find('.deck-cost-badge').first().appendText(deck.deck_price?' $'+deck.deck_price:' -');const SRCost=' '+(deck.super||'-');const URCost=' '+(deck.ultra||'-');elem.find('.deck-cost-badge').eq(1).html(SRCost+' '+URCost);elem.find('.deck_article-card-excerpt').text(deck.deck_excerpt);elem.find('.deck_article-avatar').html('');elem.find('.deck_article-card-stats').children('span').text(deck.username);elem.find('.deck_article-card-stats').children('div').children('span').text('- '+deck.submit_date);elem.find('.deck_article-card-stats').children('div').children('div').children().first().appendText(deck.deck_views.toLocaleString());elem.find('.deck_article-card-stats').children('div').children('div').children().eq(1).appendText(deck.comments);}} ctr.find('.lazy').Lazy({defaultImage:"https://images.ygoprodeck.com/images/assets/CardBack.jpg",scrollDirection:'vertical',effect:"fadeIn",effectTime:500,threshold:0,visibleOnly:true,onError:function(element){console.log('error loading '+element.data('src'));}});} function getPieChart(sel){let elm=sel;if(typeof(sel)==='string') elm=document.querySelector(sel);if(!elm){console.warn('Piechart with selector \''+sel+'\' not found.');return null;} if(!elm.classList.contains('piechart-container')){console.log('Element with selector \''+sel+'\' is not a pie chart (.piechart-container missing).');return null;} return elm;} function initPiechart(sel,total,shift){const pie=getPieChart(sel);if(!pie)return;jQuery(pie).empty();pie.piechartShift=(((shift||0)%1)+1)%1;pie.piechartCurrent=0;pie.piechartTotal=total;} function getPiechartRenderProgress(sel){const pie=getPieChart(sel);if(!pie)return{current:0,total:0};return{current:pie.piechartCurrent,total:pie.piechartTotal};} function renderPieSlice(sel,label,img,value,onClick){const pie=getPieChart(sel);if(!pie)return;const slice=jQuery('').prop('title',label+' ('+value+')').css('background-image',img);if(value2*Math.PI*(((pie.piechartCurrent/pie.piechartTotal)+pie.piechartShift)%1-.25));let startingRadians=getRadians();pie.piechartCurrent+=value;let endingRadians=getRadians();const extremesPerSector=['calc(100% - 2px) 0%','calc(100% - 2px) calc(100% - 2px)','0% calc(100% - 2px)','0% 0%'];const pointForXY=((x,y,d)=>('calc('+((1+x)*50)+'% - '+d*y+'px) calc('+((1+y)*50)+'% + '+d*x+'px)'));const sectorForXY=((x,y)=>((x>=0)?((y<=0)?0:1):((y>=0)?2:3)));const startingX=Math.cos(startingRadians);const startingY=Math.sin(startingRadians);const startingSector=sectorForXY(startingX,startingY);const endingX=Math.cos(endingRadians);const endingY=Math.sin(endingRadians);const endingSector=sectorForXY(endingX,endingY);const coveredSectors=[];const goesBackwards=((endingSector{const a=coveredSectors.indexOf(one);return(a>=0)&&(coveredSectors[a+1]==two);});const leftEdge=(coversBothInOrder(2,3)?-1:Math.min(startingX,endingX,0))/2+.5;const rightEdge=(coversBothInOrder(0,1)?1:Math.max(startingX,endingX,0))/2+.5;const topEdge=(coversBothInOrder(3,0)?-1:Math.min(startingY,endingY,0))/2+.5;const bottomEdge=(coversBothInOrder(1,2)?1:Math.max(startingY,endingY,0))/2+.5;const backgroundSize=Math.max(rightEdge-leftEdge,bottomEdge-topEdge);const leftBackgroundImageEdge=(leftEdge+rightEdge-backgroundSize)/2;const topBackgroundImageEdge=(topEdge+bottomEdge-backgroundSize)/2;slice.css('clip-path','polygon('+clipPath.join(',')+')').css('background-size',backgroundSize*100+'% '+backgroundSize*100+'%').css('background-position-x','calc('+leftBackgroundImageEdge+' * var(--piechart-size))').css('background-position-y','calc('+topBackgroundImageEdge+' * var(--piechart-size))');}else{slice.css('background-size','100% 100%');} if(onClick) slice.click(onClick);slice.appendTo(pie);return slice;} function render_deck_preview(data){function generateCardHtml(deck){const cards=[];deck.forEach(cardId=>{const existingCard=cards.find(card=>card.id===cardId);if(existingCard){existingCard.quantity++;}else{cards.push({id:cardId,quantity:1});}});return cards.map(card=>{const quantityDisplay=card.quantity>1?`x${card.quantity}`:'';return `
${card.id} ${quantityDisplay}
`;}).join('');} let extraDeckHtml=data.extradeck.length>0?`
Extra Deck
${generateCardHtml(data.extradeck)}
`:'';let sideDeckHtml=data.sidedeck.length>0?`
Side Deck
${generateCardHtml(data.sidedeck)}
`:'';let deckClasses=`deck-preview-tooltip-${data.extradeck.length>0&&data.sidedeck.length>0?'two-column':'full-width'}`;let decksContainer='';if(data.extradeck.length>0||data.sidedeck.length>0){decksContainer=`
${extraDeckHtml} ${sideDeckHtml}
`;} let deck_preview=`
${data.deckname} ${data.decksize} cards
${generateCardHtml(data.maindeck)}
${decksContainer}
`;return deck_preview;} function render_card_preview(data){data=data['data'][0];let isMonster=data.type!=="Spell Card"&&data.type!=="Trap Card"&&data.type!=="Skill Card";let isLink=data.type==="Link Monster";let banIcons={"Banned":'https://images.ygoprodeck.com/images/assets/ban/limited_0.png',"Limited":'https://images.ygoprodeck.com/images/assets/ban/limited_1.png',"Semi-Limited":'https://images.ygoprodeck.com/images/assets/ban/limited_2.png'};const isTouchDevice='ontouchstart'in window||navigator.maxTouchPoints>0;let tcgBanStatus=data.banlist_info&&data.banlist_info.ban_tcg?data.banlist_info.ban_tcg:'';let ocgBanStatus=data.banlist_info&&data.banlist_info.ban_ocg?data.banlist_info.ban_ocg:'';let tcgBan=tcgBanStatus&&banIcons[tcgBanStatus]?`
TCG: ${tcgBanStatus}
`:'';let ocgBan=ocgBanStatus&&banIcons[ocgBanStatus]?`
OCG: ${ocgBanStatus}
`:'';let cardMarketPrice=data.card_prices&&data.card_prices[0]&&data.card_prices[0].cardmarket_price?data.card_prices[0].cardmarket_price:'';let cardTcgPlayerPrice=data.card_prices&&data.card_prices[0]&&data.card_prices[0].tcgplayer_price?data.card_prices[0].tcgplayer_price:'';let card_preview=`
${true?` `:''}
${data.name}
${isMonster?`
${data.attribute}
`:`
${data.type}
${data.race}
`}
${isMonster?`
[${data.race}/${data.type}]
${!isLink?`
${data.level}
`:''}
`:''} ${isMonster?`
ATK/${data.atk} ${isLink?`LINK-${data.linkval}`:`DEF/${data.def}`}
`:''}
${data.desc.replace(/\n/g,'
')}
${tcgBan}${ocgBan}
`;return card_preview;}