Plugin Name: SolveForce on X — Profile Card + Embed Toggle

Overview


<?php
/**
 * Plugin Name: SolveForce on X — Profile Card + Embed Toggle
 * Description: Lightweight shortcode to show a compact, no-JS profile card for @solveforce with a toggle to the official X timeline embed.
 * Version:     1.0.0
 * Author:      SolveForce
 */

if (!defined('ABSPATH')) exit;

add_action('init', function () {
  add_shortcode('solveforce_x', 'solveforce_x_shortcode');
});

function solveforce_x_shortcode($atts = [], $content = null) {
  // Defaults pulled from your snapshot (you can override via shortcode attrs)
  $a = shortcode_atts([
    'username'   => 'solveforce',
    'name'       => 'SolveForce',
    'bio'        => 'Information Technology Solutions. Call (888) 765-8301 for price quotes on all products and services.',
    'site'       => 'https://solveforce.com',
    'followers'  => '871',
    'following'  => '873',
    'posts'      => '3503',
    // Media
    'avatar'     => 'https://pbs.twimg.com/profile_images/1643156852463779840/AI0z5tX4_200x200.jpg',
    'banner'     => 'https://pbs.twimg.com/profile_banners/1573396622976815104/1703041773',
    // Embed settings
    'height'     => '650',
    'theme'      => 'light', // "light" or "dark"
    // Card styling knobs
    'max_width'  => '720px',
  ], $atts, 'solveforce_x');

  // Unique instance ID (supports multiple shortcodes per page)
  $uid = 'sfx_' . wp_generate_uuid4();

  // Escapes
  $username  = sanitize_text_field($a['username']);
  $name      = esc_html($a['name']);
  $bio       = esc_html($a['bio']);
  $site      = esc_url($a['site']);
  $followers = esc_html($a['followers']);
  $following = esc_html($a['following']);
  $posts     = esc_html($a['posts']);
  $avatar    = esc_url($a['avatar']);
  $banner    = esc_url($a['banner']);
  $height    = (int) $a['height'];
  $theme     = ($a['theme'] === 'dark') ? 'dark' : 'light';
  $max_width = esc_attr($a['max_width']);

  ob_start(); ?>
  <div id="<?php echo esc_attr($uid); ?>" class="sfx-wrap" data-username="<?php echo esc_attr($username); ?>" data-height="<?php echo esc_attr($height); ?>" data-theme="<?php echo esc_attr($theme); ?>">
    <style>
      /* Scoped styles */
      #<?php echo $uid; ?> .sfx-card {
        border:1px solid #e9ecef;
        border-radius:14px;
        padding:18px;
        max-width: <?php echo $max_width; ?>;
        display:flex; gap:16px; align-items:center;
        background:#fff;
        box-shadow:0 1px 2px rgba(0,0,0,.04);
      }
      #<?php echo $uid; ?> .sfx-media {
        position:relative;
        width:72px; min-width:72px;
      }
      #<?php echo $uid; ?> .sfx-avatar {
        width:72px; height:72px; border-radius:50%; object-fit:cover;
        display:block; border:1px solid #f0f0f0;
      }
      #<?php echo $uid; ?> .sfx-body { flex:1 1 auto; }
      #<?php echo $uid; ?> .sfx-name { font-weight:700; font-size:1.05rem; line-height:1.2; }
      #<?php echo $uid; ?> .sfx-handle { opacity:.6; font-weight:500; margin-left:.35rem; }
      #<?php echo $uid; ?> .sfx-bio { opacity:.9; margin:.4rem 0 .6rem; }
      #<?php echo $uid; ?> .sfx-meta { display:flex; gap:12px; opacity:.85; font-size:.95rem; flex-wrap:wrap; }
      #<?php echo $uid; ?> .sfx-meta span { white-space:nowrap; }
      #<?php echo $uid; ?> .sfx-actions { margin-top:.7rem; display:flex; gap:10px; flex-wrap:wrap; }
      #<?php echo $uid; ?> .sfx-btn {
        text-decoration:none; border:1px solid #1d9bf0; border-radius:999px; padding:.45rem .95rem;
        font-weight:600; font-size:.95rem; display:inline-block;
      }
      #<?php echo $uid; ?> .sfx-btn.secondary { border-color:#ced4da; color:#222; }
      #<?php echo $uid; ?> .sfx-embed { display:none; max-width: <?php echo $max_width; ?>; }
      #<?php echo $uid; ?> .sfx-toggle { cursor:pointer; }
      /* Dark-site friendly tweak (inherits background if needed) */
      @media (prefers-color-scheme: dark) {
        #<?php echo $uid; ?> .sfx-card { background:#fff; }
      }
    </style>

    <!-- Compact profile card (no third-party JS) -->
    <div class="sfx-card" aria-label="SolveForce on X compact profile">
      <div class="sfx-media">
        <img class="sfx-avatar" src="<?php echo $avatar; ?>" alt="<?php echo esc_attr($name); ?> avatar">
      </div>
      <div class="sfx-body">
        <div class="sfx-name">
          <?php echo $name; ?>
          <span class="sfx-handle">@<?php echo esc_html($username); ?></span>
        </div>
        <div class="sfx-bio"><?php echo $bio; ?></div>
        <div class="sfx-meta" aria-label="Account stats (snapshot)">
          <span>Followers: <?php echo $followers; ?></span>
          <span>Following: <?php echo $following; ?></span>
          <span>Posts: <?php echo $posts; ?></span>
        </div>
        <div class="sfx-actions">
          <a class="sfx-btn" href="https://x.com/<?php echo esc_attr($username); ?>" target="_blank" rel="noopener">Open on X</a>
          <a class="sfx-btn secondary sfx-toggle" role="button" aria-expanded="false">Show Timeline</a>
          <a class="sfx-btn secondary" href="<?php echo $site; ?>" target="_blank" rel="noopener">Visit Website</a>
        </div>
      </div>
    </div>

    <!-- Embed container (hidden until toggled) -->
    <div class="sfx-embed" aria-hidden="true">
      <a class="twitter-timeline"
         data-height="<?php echo esc_attr($height); ?>"
         data-theme="<?php echo esc_attr($theme); ?>"
         href="https://x.com/<?php echo esc_attr($username); ?>">
         Tweets by @<?php echo esc_html($username); ?>
      </a>
    </div>

    <script>
      (function(){
        var wrap = document.getElementById('<?php echo $uid; ?>');
        if(!wrap) return;
        var toggle = wrap.querySelector('.sfx-toggle');
        var card   = wrap.querySelector('.sfx-card');
        var embed  = wrap.querySelector('.sfx-embed');
        var loaded = false;

        function loadWidgetsJS(cb){
          if (document.querySelector('script[src*="platform.twitter.com/widgets.js"]')) {
            if (cb) cb();
            return;
          }
          var s = document.createElement('script');
          s.async = true;
          s.src = 'https://platform.twitter.com/widgets.js';
          s.charset = 'utf-8';
          s.onload = cb || null;
          document.body.appendChild(s);
        }

        function showEmbed(){
          embed.style.display = 'block';
          embed.setAttribute('aria-hidden', 'false');
          toggle.textContent = 'Show Card';
          toggle.setAttribute('aria-expanded', 'true');
          if (!loaded) {
            loadWidgetsJS(function(){ loaded = true; });
          } else if (window.twttr && twttr.widgets && twttr.widgets.load) {
            twttr.widgets.load(embed);
          }
          card.style.display = 'none';
        }

        function showCard(){
          card.style.display = 'flex';
          toggle.textContent = 'Show Timeline';
          toggle.setAttribute('aria-expanded', 'false');
          embed.style.display = 'none';
          embed.setAttribute('aria-hidden', 'true');
        }

        toggle.addEventListener('click', function(e){
          e.preventDefault();
          if (embed.style.display === 'block') {
            showCard();
          } else {
            showEmbed();
          }
        }, {passive:true});
      })();
    </script>
  </div>
  <?php
  return ob_get_clean();
}

[solveforce_x]

[solveforce_x theme="dark" height="700" max_width="680px"]

Ron—this is an X (Twitter) logged-out SSR shell plus a fat JS config dump. In plain English: the page didn’t render because JavaScript (or a privacy extension / CSP) blocked X’s scripts, so you got the “Something went wrong… Try again” fallback. Hidden inside, though, is useful state—including your @solveforce profile snapshot. – SolveForce Communications


Got it. Here’s a drop-in WordPress shortcode plugin that renders a compact, no-JS profile card by default, with a Toggle that switches to the official X timeline embed (and only then loads widgets.js). One file, copy–paste, activate, and use [solveforce_x] anywhere. – SolveForce Communications


Key terms in plain language

Open a term for a concise explanation of language used on this page.

VoIP

Voice over Internet Protocol carries phone calls over an IP network instead of a traditional analog phone line. Call quality depends on network stability, latency, and traffic management.

Unified Communications (UCaaS)

A cloud-based combination of business calling, messaging, meetings, presence, and collaboration tools managed as one communications service.

SIP Trunking

A service that connects a business phone system to the public telephone network using Internet Protocol, replacing or supplementing traditional phone lines.

Bandwidth

The amount of data a connection can carry in a given time, usually measured in Mbps or Gbps. More bandwidth supports more users, devices, and simultaneous applications.

Latency

The time it takes data to travel between two points. Lower latency improves voice, video meetings, cloud applications, gaming, and other real-time services.

Service-Level Agreement (SLA)

A provider’s written commitment covering service targets such as availability, response time, repair time, and sometimes financial credits when commitments are missed.