PageSourceSearch

https://wpamelia.com/wp-content/themes/amelia-theme/amelia-blocks/assets/js/pricing-block.js?ver=1785146537

js wpamelia.com collected 2026-10-02 02:29:08 UTC 5,200 bytes, 143 lines download raw bytes

1/**
2 * Pricing Block JavaScript
3 * Handles annual/lifetime toggle and Paddle integration
4 */
5
6document.addEventListener('DOMContentLoaded', function() {
7    const pricingToggles = document.querySelectorAll('[data-pricing-toggle]');
8    
9    pricingToggles.forEach(toggle => {
10        const options = toggle.querySelectorAll('.pricing-toggle__option');
11        const blockContainer = toggle.closest('.pricing-block') || toggle.closest('.pricing-tables');
12        
13        if (!blockContainer) return;
14        
15        const grid = blockContainer.querySelector('[data-pricing-grid]');
16        
17        if (!grid) return;
18        
19        options.forEach(option => {
20            option.addEventListener('click', function() {
21                const mode = this.getAttribute('data-mode');
22                
23                // Update active state
24                options.forEach(opt => opt.classList.remove('pricing-toggle__option--active'));
25                this.classList.add('pricing-toggle__option--active');
26                
27                // Update cards visibility and pricing
28                updateCardsForMode(grid, mode);
29            });
30        });
31    });
32});
33
34/**
35 * Update cards visibility based on pricing mode
36 * @param {Element} grid - The pricing grid container
37 * @param {string} mode - 'annual' or 'lifetime'
38 */
39function updateCardsForMode(grid, mode) {
40    const cards = grid.querySelectorAll('.pricing-card');
41    
42    cards.forEach(card => {
43        const cardMode = card.getAttribute('data-card-mode');
44        
45        if (cardMode === mode) {
46            card.style.display = 'flex';
47            card.classList.remove('pricing-card--hidden');
48        } else {
49            card.style.display = 'none';
50            card.classList.add('pricing-card--hidden');
51        }
52    });
53}
54
55// Expose function globally for comparison table sync
56window.updatePricingBlockForMode = updateCardsForMode;
57
58/**
59 * Update cards visibility based on pricing mode
60 * @param {Element} grid - The pricing grid container
61 * @param {string} mode - 'annual' or 'lifetime'
62 */
63function updateCardsVisibility(grid, mode) {
64    const cards = grid.querySelectorAll('.pricing-card');
65    
66    cards.forEach(card => {
67        const showInAnnual = card.getAttribute('data-show-annual') === 'yes';
68        const showInLifetime = card.getAttribute('data-show-lifetime') === 'yes';
69        
70        let shouldShow = false;
71        
72        if (mode === 'annual' && showInAnnual) {
73            shouldShow = true;
74        } else if (mode === 'lifetime' && showInLifetime) {
75            shouldShow = true;
76        }
77        
78        if (shouldShow) {
79            card.style.display = 'flex';
80            card.classList.remove('pricing-card--hidden');
81        } else {
82            card.style.display = 'none';
83            card.classList.add('pricing-card--hidden');
84        }
85    });
86}
87
88/**
89 * Handle Show More/Less functionality for pricing card features
90 */
91function initShowMoreButtons() {
92    const showMoreButtons = document.querySelectorAll('[data-show-more]');
93
94    showMoreButtons.forEach(button => {
95        const card = button.closest('.pricing-card');
96        if (!card) return;
97
98        // Wrap hidden features in a container for smooth animation
99        const hiddenFeatures = card.querySelectorAll('.pricing-card__feature-item--hidden');
100        if (hiddenFeatures.length === 0) return;
101
102        const container = document.createElement('div');
103        container.className = 'pricing-card__hidden-features-container';
104        hiddenFeatures[0].parentNode.insertBefore(container, hiddenFeatures[0]);
105        hiddenFeatures.forEach(f => container.appendChild(f));
106
107        button.addEventListener('click', function(e) {
108            e.preventDefault();
109
110            const isExpanded = this.classList.contains('active');
111
112            if (isExpanded) {
113                // Collapse: pin current height then animate to 0
114                container.style.maxHeight = container.scrollHeight + 'px';
115                requestAnimationFrame(() => {
116                    requestAnimationFrame(() => {
117                        container.style.maxHeight = '0';
118                        container.style.opacity = '0';
119                    });
120                });
121                this.classList.remove('active');
122                this.querySelector('.show-more-text').textContent = 'Show More';
123            } else {
124                // Expand: animate to full height then release constraint
125                container.style.maxHeight = container.scrollHeight + 'px';
126                container.style.opacity = '1';
127                container.addEventListener('transitionend', function onEnd(ev) {
128                    if (ev.propertyName === 'max-height') {
129                        container.style.maxHeight = 'none';
130                        container.removeEventListener('transitionend', onEnd);
131                    }
132                });
133                this.classList.add('active');
134                this.querySelector('.show-more-text').textContent = 'Show Less';
135            }
136        });
137    });
138}
139
140// Initialize show more buttons on page load
141document.addEventListener('DOMContentLoaded', function() {
142    initShowMoreButtons();
143});

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.