fixed wp plugin

This commit is contained in:
2025-04-16 16:13:31 +02:00
parent 78ab65fccf
commit 3a7f791fa9
18 changed files with 921 additions and 693 deletions
@@ -0,0 +1,40 @@
/**
* Palantics Admin Styles
*/
.palantics-heading {
color: #007cba;
font-weight: bold;
}
.palantics-methods-container {
background-color: #fff;
padding: 20px;
margin-top: 20px;
border: 1px solid #ccc;
border-radius: 4px;
}
.palantics-method {
margin-bottom: 20px;
}
.palantics-method-title {
font-size: 16px;
font-weight: bold;
margin-bottom: 10px;
}
.palantics-code-sample {
background-color: #f5f5f5;
padding: 10px;
border-radius: 4px;
font-family: monospace;
margin-top: 5px;
}
.palantics-description {
margin-top: 5px;
font-size: 13px;
color: #666;
}
@@ -0,0 +1,2 @@
<?php
// silence is golden
@@ -0,0 +1,26 @@
/**
* Palantics Tracking Block Styles
*/
.palantics-tracking-block-wrapper {
border: 1px dashed #007cba;
padding: 10px;
position: relative;
}
.palantics-tracking-block-notice {
background: #007cba;
color: white;
padding: 5px 10px;
font-size: 12px;
position: absolute;
top: 0;
right: 0;
border-bottom-left-radius: 4px;
display: flex;
align-items: center;
}
/* Frontend styles */
/*
.palantics-tracking-wrapper {
} */
@@ -0,0 +1,2 @@
<?php
// silence is golden
@@ -0,0 +1,87 @@
/**
* Palantics Tracking Block
*/
const { registerBlockType } = wp.blocks;
const { InspectorControls } = wp.blockEditor;
const { PanelBody, TextControl } = wp.components;
const { Fragment } = wp.element;
const { __ } = wp.i18n;
// Register the block
registerBlockType('palantics-tracking/track-element', {
title: __('Tracking Element', 'palantics-tracking-plugin'),
icon: 'chart-line',
category: 'widgets',
keywords: [
__('track', 'palantics-tracking-plugin'),
__('analytics', 'palantics-tracking-plugin'),
__('palantics', 'palantics-tracking-plugin'),
],
attributes: {
eventName: {
type: 'string',
default: 'tracked_element',
},
content: {
type: 'string',
default: '',
},
},
edit: function(props) {
const { attributes, setAttributes } = props;
const { eventName, content } = attributes;
return (
<Fragment>
<InspectorControls>
<PanelBody title={__('Tracking Settings', 'palantics-tracking-plugin')}>
<TextControl
label={__('Event Name', 'palantics-tracking-plugin')}
value={eventName}
onChange={(value) => setAttributes({ eventName: value })}
help={__('Enter the event name that will be used for tracking this element', 'palantics-tracking-plugin')}
/>
</PanelBody>
</InspectorControls>
<div
className="palantics-tracking-block"
style={{
padding: '20px',
border: '1px dashed #ccc',
backgroundColor: '#f8f8f8'
}}
>
<div style={{ marginBottom: '10px', fontWeight: 'bold' }}>
{__('Palantics Tracking Element', 'palantics-tracking-plugin')}
</div>
<div style={{ fontSize: '0.9em', marginBottom: '10px' }}>
{__('Event:', 'palantics-tracking-plugin')} <code>{eventName}</code>
</div>
<div style={{ fontStyle: 'italic', fontSize: '0.8em' }}>
{__('This element will be tracked when clicked', 'palantics-tracking-plugin')}
</div>
</div>
</Fragment>
);
},
save: function(props) {
const { attributes } = props;
const { eventName } = attributes;
return (
<div
className="palantics-tracking-wrapper"
onClick={`tE('${eventName}')`}
>
<div className="palantics-tracking-content">
{props.children}
</div>
</div>
);
},
});
@@ -0,0 +1,87 @@
/**
* Palantics class-based tracking script
*/
document.addEventListener('DOMContentLoaded', function() {
// Helper function to get element details for tracking
function getElementDetails(element) {
const details = {};
// Get element text or alternative
if (element.textContent && element.textContent.trim()) {
details.text = element.textContent.trim();
} else if (element.placeholder) {
details.text = element.placeholder;
} else if (element.value) {
details.text = element.value;
} else if (element.alt) {
details.text = element.alt;
} else if (element.getAttribute('aria-label')) {
details.text = element.getAttribute('aria-label');
}
// Limit text length
if (details.text && details.text.length > 50) {
details.text = details.text.substring(0, 47) + '...';
}
// Get element ID, class and href if available
if (element.id) {
details.id = element.id;
}
if (element.className) {
details.class = element.className;
}
if (element.href) {
const href = element.href;
// Only include if it's not too long
if (href.length < 100) {
details.href = href;
}
}
return details;
}
// Function to initialize tracking for a specific class
function initializeClassTracking(className) {
const elements = document.querySelectorAll('.' + className);
elements.forEach(function(element) {
element.addEventListener('click', function(e) {
const details = getElementDetails(element);
tE('custom_element_click', {
element: 'custom',
class: className,
...details
});
});
});
}
// Track elements with data-track attribute
function initializeDataAttributeTracking() {
const trackedElements = document.querySelectorAll('[data-track]');
trackedElements.forEach(function(element) {
element.addEventListener('click', function(e) {
const eventName = element.getAttribute('data-track') || 'tracked_element';
const details = getElementDetails(element);
tE(eventName, {
element: 'data-track',
...details
});
});
});
}
// Initialize data attribute tracking
initializeDataAttributeTracking();
// If trackClasses is defined (will be injected by WordPress), initialize class tracking
if (typeof trackClasses !== 'undefined' && Array.isArray(trackClasses)) {
trackClasses.forEach(function(className) {
initializeClassTracking(className);
});
}
});
@@ -0,0 +1,2 @@
<?php
// silence is golden
@@ -0,0 +1,95 @@
/**
* Palantics main tracking script
*/
// Initialize tracking function
function tE(eventName, additionalParams = {}) {
// Create tracking data object
const data = {
event: eventName,
url: window.location.href,
ref: document.referrer,
ua: navigator.userAgent,
sw: window.screen.width,
lang: navigator.language || navigator.userLanguage,
};
// Add any additional parameters
Object.assign(data, additionalParams);
// Helper function to serialize an object into URL parameters
function serializeObject(obj, prefix) {
const str = [];
for (const p in obj) {
if (obj.hasOwnProperty(p)) {
const k = prefix ? prefix + "[" + p + "]" : p;
const v = obj[p];
if (v !== null && typeof v === "object") {
str.push(serializeObject(v, k));
} else {
str.push(encodeURIComponent(k) + "=" + encodeURIComponent(v));
}
}
}
return str.join("&");
}
// Function for sending tracking data
function sendInfo() {
try {
// Get site URL and prepare REST API endpoint URL
const siteUrl = window.location.origin;
const restApiEndpoint = `${siteUrl}/wp-json/palantics/v1/sun`;
// Use POST request with data in body and query string
fetch(restApiEndpoint + '?' + serializeObject(data), {
method: "POST",
mode: "no-cors",
cache: "no-cache",
credentials: "omit", // Don't send cookies
headers: {
"X-Final-Destination": server, // Pass the final destination
"Content-Type": "application/json"
},
keepalive: true, // Ensures request completes even if page unloads
})
.catch(e => {
console.error("Tracking error:", e);
// If POST fails, try GET as fallback
fetch(restApiEndpoint + '?' + serializeObject(data), {
method: "GET",
mode: "no-cors",
cache: "no-cache",
credentials: "omit",
headers: {
"X-Final-Destination": server
},
keepalive: true,
}).catch(e2 => {
console.error("Fallback tracking error:", e2);
});
});
return true;
} catch (e) {
console.error("Tracking error:", e);
}
}
return sendInfo();
}
// Page load tracking function
function pL() {
tE("pageLoad_" + window.location.pathname);
}
// Set up page load tracking
document.addEventListener("DOMContentLoaded", function() {
try {
pL();
} catch (error) {
console.error("Error in page load tracking:", error);
}
});