Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
134 changes: 133 additions & 1 deletion themes/arm-design-system-hugo-theme/static/js/anonymous-analytics.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,10 @@
- list-card --> learning path and tool list cards should have these types
- learning-path-nav --> navigation buttons in the application: 'next' button, 'prev' button, left-hand navigation
- metadata --> any metadata links; above LPs and installs, and in 'next steps' page
- content --> all links from user-generated markdown should have this. the 'render-link.html' should implement this tracker
- content --> all links from user-generated markdown should have this, INCLUDING CODE. the 'render-link.html' should implement this tracker
- data-track-name --> specific name of the element, human readable to link behavior. A click on a learning path should render its title, etc. This is dynamic
- data-track-identifier --> Prism language of a code block
- data-track-url --> full page URL for code copy events

- facet-interaction
Attributes tracked:
Expand All @@ -28,6 +30,12 @@
Attributes tracked:
- feedback-type --> either 'star-rating' or 'reason'
- feedback-content --> specifies the feedback. Star-rating will be 1-5, Reason will be a string (from a limited choice set, not free text)

- copy-type
Attributes tracked:
- data-track-type --> copy-type
- data-track-location --> manual-copy or button-copy
- data-track-name --> current page number and name

*/

Expand Down Expand Up @@ -168,6 +176,90 @@ function attachPageFindSearchTracker() {
}


function getSelectedCodeBlock() {
const selection = window.getSelection();

if (!selection || selection.isCollapsed || selection.rangeCount === 0) {
return null;
}

const range = selection.getRangeAt(0);

function getContainingPre(node) {
const element = node.nodeType === Node.ELEMENT_NODE
? node
: node.parentElement;

return element?.closest('.code-toolbar pre') || null;
}

const start_pre = getContainingPre(range.startContainer);
const end_pre = getContainingPre(range.endContainer);

// Only track selections contained within one Prism code block.
if (!start_pre || start_pre !== end_pre) {
return null;
}

return start_pre;
}


function getCodeBlockLanguage(pre_element) {
const code_element = pre_element.querySelector('code');
const language_class = Array.from(code_element?.classList || [])
.find((class_name) => class_name.startsWith('language-'));

return language_class
? language_class.replace('language-', '')
: 'unknown';
}


function getCodeCopyTrackName() {
const active_learning_path_step = document.getElementById('learning-path-step-active');

if (active_learning_path_step) {
const page_number = parseInt(active_learning_path_step.getAttribute('data-step-num')) + 1;
const page_name = (active_learning_path_step.innerText || active_learning_path_step.textContent).trim();

return 'page_number:'+page_number+','+'page_name:'+page_name;
}

const install_guide_title = document.getElementById('install-guide-title');

if (install_guide_title) {
const page_name = (install_guide_title.innerText || install_guide_title.textContent).trim();

return 'page_number:1,'+'page_name:'+page_name;
}

return window.location.pathname;
}


function trackCodeCopy(copy_location, pre_element) {
const code_block_language = getCodeBlockLanguage(pre_element);
const track_str = getCodeCopyTrackName();

if (window._satellite?.track) {
window._satellite.track('content-interaction', {
'data-track-type' : 'copy',
'data-track-location' : 'content',
'data-track-name' : track_str,
'data-track-identifier' : code_block_language,
'data-track-url' : window.location.href
});

window._satellite.track('content-interaction', {
'data-track-type' : 'copy-type',
'data-track-location' : copy_location,
'data-track-name' : track_str
});
}
}


// Go page by page, and assign the analytics tracker event component to appropriate ares.


Expand All @@ -177,6 +269,46 @@ function attachPageFindSearchTracker() {
let depth_of_path= current_path.split('/').length - 1 // Get number of '/' in the string; will help identify where we are in the heirarcy


//
// Prism code blocks
// ===================
// Use delegated listeners because Prism creates its toolbar buttons after
// the page DOM is ready. These listeners cover Learning Paths and install
// guides and identify each copied code block by its Prism language.

// Track keyboard and context-menu copies of a selection in a code block.
document.addEventListener('copy', function() {
const pre_element = getSelectedCodeBlock();

if (pre_element) {
trackCodeCopy('manual-copy', pre_element);
}
});

// Track use of Prism's copy-to-clipboard toolbar button.
document.addEventListener('click', function(event) {
if (!(event.target instanceof Element)) {
return;
}

const copy_button = event.target.closest('button.copy-to-clipboard-button');

if (!copy_button) {
return;
}

const pre_element = copy_button
.closest('.code-toolbar')
?.querySelector('pre');

if (!pre_element) {
return;
}

trackCodeCopy('button-copy', pre_element);
});


//
// Header
// ===================
Expand Down
2 changes: 2 additions & 0 deletions tools/social_card_generation/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
# Commercial fonts - do not commit
fonts/*.otf
23 changes: 23 additions & 0 deletions tools/social_card_generation/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
# Social Card Prototype

Prototype generator for learn.arm.com social/Open Graph cards with updated branding and name of the content directly in the image. It reads a Learning Path or install guide Markdown file, pulls the `title` from front matter, applies the content type label, and writes `social_image.webp`.

To implement this we need to put this script in our CI pipeline for each content (and when its title is updated). Each content needs to generate a unique webp image for each learning path for social sharing, as opposed to the current one social image approach. The Hugo template needs to be updated for each content to source its webp.


You'll need these python files installed:
```bash
pip install playwright Pillow
python -m playwright install --only-shell chromium
```

Test from the repo root:

```bash
python tools/social_card_prototype/generate.py content/install-guides/ambaviz.md
python tools/social_card_prototype/generate.py content/learning-paths/embedded-and-microcontrollers/advanced_soc
```

Open `tools/social_card_prototype/social_image.webp` to inspect the result.

Exact brand rendering still needs a font solution for `fonts/Aeonik-Medium.otf` and `fonts/AeonikFono-Regular.otf`, which I have from our branding team but we are unable to host in the OSS repo on GitHub due to licensing. The current system font fallbacks are near-identical and OK for social sharing.
Empty file.
Loading
Loading