array( 'label' => 'Facebook', 'icon' => 'fab fa-facebook-f', 'color' => '#1877F2' ), 'instagram_url' => array( 'label' => 'Instagram', 'icon' => 'fab fa-instagram', 'color' => '#E4405F' ), 'youtube_url' => array( 'label' => 'YouTube', 'icon' => 'fab fa-youtube', 'color' => '#FF0000' ), 'twitter_url' => array( 'label' => 'X (Twitter)', 'icon' => 'svg-x', 'color' => '#000000' ), 'linkedin_url' => array( 'label' => 'LinkedIn', 'icon' => 'fab fa-linkedin-in', 'color' => '#0A66C2' ), 'tiktok_url' => array( 'label' => 'TikTok', 'icon' => 'fab fa-tiktok', 'color' => '#000000' ), 'yelp_url' => array( 'label' => 'Yelp', 'icon' => 'fab fa-yelp', 'color' => '#D32323' ), 'google_business_url' => array( 'label' => 'Google', 'icon' => 'fab fa-google', 'color' => '#4285F4' ), 'pinterest_url' => array( 'label' => 'Pinterest', 'icon' => 'fab fa-pinterest-p', 'color' => '#E60023' ), 'bbb_url' => array( 'label' => 'BBB', 'icon' => 'fas fa-shield-alt', 'color' => '#006CB7' ), 'nextdoor_url' => array( 'label' => 'Nextdoor', 'icon' => 'fas fa-home', 'color' => '#8ED500' ), 'houzz_url' => array( 'label' => 'Houzz', 'icon' => 'fab fa-houzz', 'color' => '#4DBC15' ), 'angi_url' => array( 'label' => 'Angi', 'icon' => 'fas fa-tools', 'color' => '#FF6153' ), 'thumbtack_url' => array( 'label' => 'Thumbtack', 'icon' => 'fas fa-thumbtack', 'color' => '#009FD9' ), 'homeadvisor_url' => array( 'label' => 'HomeAdvisor', 'icon' => 'fas fa-home', 'color' => '#EF6C00' ), ); $available = array(); if ( $vars ) { foreach ( $all_platforms as $key => $data ) { if ( ! empty( $vars[ $key ] ) ) { $available[ $key ] = array_merge( $data, array( 'url' => $vars[ $key ] ) ); } } } return $available; } /** * Register widget controls. * * Uses Elementor's selectors system for all color controls so that * global colors are properly resolved on both frontend and editor. */ protected function register_controls() { // Content Section $this->start_controls_section( 'content_section', array( 'label' => __( 'Content', 'a1-tools' ), 'tab' => \Elementor\Controls_Manager::TAB_CONTENT, ) ); // Show which platforms are available $platforms = $this->get_available_platforms(); if ( ! empty( $platforms ) ) { $platform_names = array_map( function( $p ) { return $p['label']; }, $platforms ); $this->add_control( 'info_notice', array( 'type' => \Elementor\Controls_Manager::RAW_HTML, 'raw' => sprintf( /* translators: %s: comma-separated list of social media platform names */ __( 'Available platforms: %s

Configure more in the A1 Tools dashboard.', 'a1-tools' ), implode( ', ', $platform_names ) ), 'content_classes' => 'elementor-panel-alert elementor-panel-alert-success', ) ); } else { $this->add_control( 'info_notice', array( 'type' => \Elementor\Controls_Manager::RAW_HTML, 'raw' => __( 'No social media URLs configured.

Add them in the A1 Tools dashboard under Site Variables.', 'a1-tools' ), 'content_classes' => 'elementor-panel-alert elementor-panel-alert-warning', ) ); } $this->end_controls_section(); // Style Section $this->start_controls_section( 'style_section', array( 'label' => __( 'Style', 'a1-tools' ), 'tab' => \Elementor\Controls_Manager::TAB_STYLE, ) ); $this->add_control( 'icon_style', array( 'label' => __( 'Style', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::SELECT, 'default' => 'default', 'options' => array( 'default' => __( 'Official Colors', 'a1-tools' ), 'outline' => __( 'Outline', 'a1-tools' ), 'minimal' => __( 'Minimal (Icons Only)', 'a1-tools' ), 'light' => __( 'Light Background', 'a1-tools' ), 'dark' => __( 'Dark Background', 'a1-tools' ), 'custom' => __( 'Custom Colors', 'a1-tools' ), ), ) ); $this->add_control( 'shape', array( 'label' => __( 'Shape', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::SELECT, 'default' => 'rounded', 'options' => array( 'rounded' => __( 'Rounded', 'a1-tools' ), 'circle' => __( 'Circle', 'a1-tools' ), 'square' => __( 'Square', 'a1-tools' ), ), 'selectors_dictionary' => array( 'rounded' => '8px', 'circle' => '50%', 'square' => '0', ), 'selectors' => array( '{{WRAPPER}} .a1tools-social-icon' => 'border-radius: {{VALUE}};', ), ) ); $this->add_control( 'size', array( 'label' => __( 'Button Size', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::SLIDER, 'size_units' => array( 'px' ), 'range' => array( 'px' => array( 'min' => 20, 'max' => 100, 'step' => 1, ), ), 'default' => array( 'unit' => 'px', 'size' => 40, ), 'selectors' => array( '{{WRAPPER}} .a1tools-social-icon' => 'width: {{SIZE}}{{UNIT}}; height: {{SIZE}}{{UNIT}}; line-height: {{SIZE}}{{UNIT}};', ), ) ); $this->add_control( 'icon_size', array( 'label' => __( 'Icon Size', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::SLIDER, 'size_units' => array( 'px' ), 'range' => array( 'px' => array( 'min' => 10, 'max' => 50, 'step' => 1, ), ), 'default' => array( 'unit' => 'px', 'size' => 18, ), 'selectors' => array( '{{WRAPPER}} .a1tools-social-icon' => 'font-size: {{SIZE}}{{UNIT}};', ), ) ); $this->add_control( 'spacing', array( 'label' => __( 'Spacing', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::SLIDER, 'size_units' => array( 'px' ), 'range' => array( 'px' => array( 'min' => 0, 'max' => 30, 'step' => 1, ), ), 'default' => array( 'unit' => 'px', 'size' => 8, ), 'selectors' => array( '{{WRAPPER}} .a1tools-social-icons-styled' => 'gap: {{SIZE}}{{UNIT}};', ), ) ); $this->add_responsive_control( 'alignment', array( 'label' => __( 'Alignment', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::CHOOSE, 'options' => array( 'left' => array( 'title' => __( 'Left', 'a1-tools' ), 'icon' => 'eicon-text-align-left', ), 'center' => array( 'title' => __( 'Center', 'a1-tools' ), 'icon' => 'eicon-text-align-center', ), 'right' => array( 'title' => __( 'Right', 'a1-tools' ), 'icon' => 'eicon-text-align-right', ), ), 'default' => 'left', 'selectors_dictionary' => array( 'left' => 'flex-start', 'center' => 'center', 'right' => 'flex-end', ), 'selectors' => array( '{{WRAPPER}} .a1tools-social-icons-styled' => 'justify-content: {{VALUE}};', ), ) ); // Custom Colors - Normal state $this->add_control( 'custom_colors_heading', array( 'label' => __( 'Custom Colors', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::HEADING, 'separator' => 'before', 'condition' => array( 'icon_style' => 'custom', ), ) ); $this->add_control( 'custom_icon_color', array( 'label' => __( 'Icon Color', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::COLOR, 'default' => '#ffffff', 'condition' => array( 'icon_style' => 'custom', ), 'selectors' => array( '{{WRAPPER}} .a1tools-social-icon' => 'color: {{VALUE}};', '{{WRAPPER}} .a1tools-social-icon i' => 'color: {{VALUE}};', ), ) ); $this->add_control( 'custom_bg_color', array( 'label' => __( 'Background Color', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::COLOR, 'default' => '#F7941E', 'condition' => array( 'icon_style' => 'custom', ), 'selectors' => array( '{{WRAPPER}} .a1tools-social-icon' => 'background-color: {{VALUE}};', ), ) ); $this->add_control( 'custom_border_color', array( 'label' => __( 'Border Color', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::COLOR, 'default' => '', 'condition' => array( 'icon_style' => 'custom', ), 'selectors' => array( '{{WRAPPER}} .a1tools-social-icon' => 'border-color: {{VALUE}};', ), ) ); $this->add_control( 'custom_border_width', array( 'label' => __( 'Border Width', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::SLIDER, 'size_units' => array( 'px' ), 'range' => array( 'px' => array( 'min' => 0, 'max' => 10, 'step' => 1, ), ), 'default' => array( 'unit' => 'px', 'size' => 0, ), 'condition' => array( 'icon_style' => 'custom', ), 'selectors' => array( '{{WRAPPER}} .a1tools-social-icon' => 'border-width: {{SIZE}}{{UNIT}}; border-style: solid;', ), ) ); // Custom Colors - Hover state $this->add_control( 'custom_hover_heading', array( 'label' => __( 'Hover Colors', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::HEADING, 'separator' => 'before', 'condition' => array( 'icon_style' => 'custom', ), ) ); $this->add_control( 'custom_hover_icon_color', array( 'label' => __( 'Hover Icon Color', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::COLOR, 'default' => '', 'condition' => array( 'icon_style' => 'custom', ), 'selectors' => array( '{{WRAPPER}} .a1tools-social-icon:hover' => 'color: {{VALUE}};', '{{WRAPPER}} .a1tools-social-icon:hover i' => 'color: {{VALUE}};', ), ) ); $this->add_control( 'custom_hover_bg_color', array( 'label' => __( 'Hover Background Color', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::COLOR, 'default' => '', 'condition' => array( 'icon_style' => 'custom', ), 'selectors' => array( '{{WRAPPER}} .a1tools-social-icon:hover' => 'background-color: {{VALUE}};', ), ) ); $this->add_control( 'custom_hover_border_color', array( 'label' => __( 'Hover Border Color', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::COLOR, 'default' => '', 'condition' => array( 'icon_style' => 'custom', ), 'selectors' => array( '{{WRAPPER}} .a1tools-social-icon:hover' => 'border-color: {{VALUE}};', ), ) ); $this->end_controls_section(); // Hover Effects Section $this->start_controls_section( 'hover_section', array( 'label' => __( 'Hover Effects', 'a1-tools' ), 'tab' => \Elementor\Controls_Manager::TAB_STYLE, ) ); $this->add_control( 'hover_effect', array( 'label' => __( 'Hover Effect', 'a1-tools' ), 'type' => \Elementor\Controls_Manager::SELECT, 'default' => 'scale', 'options' => array( 'none' => __( 'None', 'a1-tools' ), 'scale' => __( 'Scale Up', 'a1-tools' ), 'lift' => __( 'Lift (Shadow)', 'a1-tools' ), 'rotate' => __( 'Rotate', 'a1-tools' ), 'pulse' => __( 'Pulse', 'a1-tools' ), ), 'prefix_class' => 'a1tools-hover-', ) ); $this->end_controls_section(); } /** * Get style dependencies for this widget. */ public function get_style_depends() { return array( 'a1tools-elementor-icons' ); } /** * Render widget output on the frontend. * * Custom colors are handled entirely by Elementor's selectors system. * Only non-custom styles (Official, Outline, etc.) need inline styles * because each icon has a different platform-specific color. */ protected function render() { $settings = $this->get_settings_for_display(); $platforms = $this->get_available_platforms(); if ( empty( $platforms ) ) { return; } $style = ! empty( $settings['icon_style'] ) ? $settings['icon_style'] : 'default'; // Output HTML - add style class for non-custom per-platform color targeting echo '
'; foreach ( $platforms as $key => $data ) { $inline_style = ''; // For non-custom styles, apply per-platform colors via inline style if ( 'custom' !== $style ) { $item_color = $data['color']; if ( 'default' === $style || 'official' === $style ) { $inline_style = 'background-color:' . esc_attr( $item_color ) . ';'; } elseif ( 'outline' === $style ) { $inline_style = 'border-color:' . esc_attr( $item_color ) . ';color:' . esc_attr( $item_color ) . ';'; } elseif ( 'minimal' === $style || 'light' === $style ) { $inline_style = 'color:' . esc_attr( $item_color ) . ';'; } } echo ''; echo wp_kses( a1tools_get_icon_html( $data['icon'] ), a1tools_icon_allowed_tags() ); echo '' . esc_html( $data['label'] ) . ''; echo ''; } echo '
'; } /** * Render widget output in the editor. * * The editor template handles the live preview. Colors for "Custom" style * are applied via Elementor's selectors (same as frontend). Non-custom styles * use inline styles for per-platform colors. */ protected function content_template() { // Get available platforms for the editor preview $platforms = $this->get_available_platforms(); // Convert to JS-friendly format $js_platforms = array(); foreach ( $platforms as $key => $data ) { $svg = a1tools_get_svg_icon( $data['icon'] ); if ( $svg ) { $js_platforms[] = array( 'svg' => $svg, 'color' => $data['color'], 'name' => $data['label'], ); } else { $icon_parts = explode( ' ', $data['icon'] ); $icon_class = end( $icon_parts ); $icon_prefix = count( $icon_parts ) > 1 ? $icon_parts[0] : 'fab'; $js_platforms[] = array( 'icon' => $icon_class, 'prefix' => $icon_prefix, 'color' => $data['color'], 'name' => $data['label'], ); } } // If no platforms available, show a placeholder if ( empty( $js_platforms ) ) { ?>

<# var style = settings.icon_style || 'default'; // Actual available platforms from the site var platforms = ; #>
<# _.each(platforms, function(platform) { var inlineStyle = ''; // For non-custom styles, apply per-platform colors inline if (style !== 'custom') { switch(style) { case 'outline': inlineStyle = 'background:transparent; border:2px solid ' + platform.color + '; color:' + platform.color + ';'; break; case 'minimal': inlineStyle = 'background:transparent; color:' + platform.color + ';'; break; case 'light': inlineStyle = 'background:#f5f5f5; color:' + platform.color + ';'; break; case 'dark': inlineStyle = 'background:#333; color:#fff;'; break; default: inlineStyle = 'background-color:' + platform.color + '; color:#fff;'; } } #> <# if (platform.svg) { #> {{{ platform.svg }}} <# } else { #> <# } #> <# }); #>