1

To place an external widget without having to let non-technical people paste embed code on every desired spot on a webpage, I'm working on a visual div and p tag selector where people can just pinpoint the desired element(s).

When people hover over an element, it will show a red border to show them what's selected.

For us to place the widget, normally we would target by class or id. However, the class / id should be unique for it to work and unique classes for a random div / p tag is pretty rare.

Via a piece of jquery code:

$(document).on('mouseenter mouseleave', '.sj-highlight', 
function (e) {

}

I can get the DOM details about the selected element. Is there a way I can target the highlighted element by using some data from the DOM details and if yes how?

Tried the code above but just don't know much about DOM selecting possibilities.

To make the whole highlight per element possible, I wrote this:

$( document ).ready(function() {

$('div, p').each(function(i){
  $(this).addClass('sj-highlight sjhighlight'+i+'');
  $(this).attr('data-sj', 'sjhighlight'+i+'');
});

$(document).on('mouseenter mouseleave', '.sj-highlight', function (e) {

var sjhighlighter = $(this).attr("data-sj");

// hide other highlights
$('.sj-highlight').css("border","2px solid transparent");

if(e.type == 'mouseenter')

    {
    $('.'+sjhighlighter+'').css("border","2px solid #ff0000");
    }

});

The end result would be to somehow target the selected elements with the DOM instead of a class or id.

Alexis Philip
  • 517
  • 2
  • 5
  • 23
Ralph
  • 132
  • 12
  • 4
    Sounds like you want `e.target` or `e.currentTarget`. A bit unclear exactly what you are trying to accomplish – charlietfl Jul 29 '19 at 14:49
  • 1
    You can just save `this` in a variable / an array inside the `mouseenter` listener; it will point to the current `HTMLElement`. –  Jul 29 '19 at 14:53
  • Hi charlietfl and Chris G, thank you for your quick response. You can view a full example here: http://smilejet.net/app/test_nu.php?load=https://www.nu.nl As you can see, I'm loading a random (Dutch) webpage and if you move your mouse over the site's elements you'll see the red border. How can I use e.target later on? I mean, how can i later on target the element with e.target? To explain it more: people click an element, i will store (for example) the e.target or currentTarget to the database. After that, we use the stored "position" later on to target that selected div. – Ralph Jul 29 '19 at 14:54
  • 1
    If you want to store the element in a database it gets a bit more complicated. You basically have to use recursion to walk up the tree until you find an element with an `id` or `body`, and build the selector like `#wrap > div:nth-child(2) > p:nth-child(5)` –  Jul 29 '19 at 14:59
  • Chris G, thanks, this also means that if they add/remove elements the recorded element "number" will be shifted, right? – Ralph Jul 29 '19 at 15:00
  • Yes; you could use the contents of the paragraph instead, but that'll bork as soon as the text changes. –  Jul 29 '19 at 15:02
  • if you explain it further it may be clearer for us, for example *when a user hovers ..... he clicks ...... later we ......* ? I hope you get what I meant. – ThS Jul 29 '19 at 15:09
  • Have done what @ChrisG is suggesting for an A/B testing app. Walking up the tree to build the string selector needed is not difficult if that is what you need – charlietfl Jul 29 '19 at 15:16
  • 1
    First of all, imo if you have to copy selector of an element then you're on a really really wrong path of solving your problem. Better describe it in detail so we can inspect it deeper. Anyway, have it if you want to copy selector - https://stackoverflow.com/questions/28804207/how-to-get-css-selector-for-an-element-using-javascript – lucifer63 Jul 29 '19 at 15:26
  • @ths if you check the link I added you'll see that when you hover your mouse over an element a red border appears, showing you that that element is selected. I somehow need to store the target' position/DOM data to a database so I can target it later to append a widget to that element. Hope it's clear now? – Ralph Jul 29 '19 at 15:45
  • @lucifer63 thanks, will check it out. Chris G the solution should be something that doesn't break when elements get added/removed. – Ralph Jul 29 '19 at 15:51

2 Answers2

0

From the pieces that i put together i think if you can get to the element using

$(document).on('mouseenter mouseleave', '.sj-highlight', 
function (e) {});

that means you already have it, because $(document).on() form works for dynamically added elements (that means even if you add element dynamically it still works properly), you can use :

var elementClass = $(this).attr('class');

and you have complete control over the element from there. And you have also all possibility over its children or it parent which returned as dom elements objects. I think that your question need a little bit of clarification too.

  • Hi Abdelhak, thank you for your answer, but if you read the description you'll see this is not what I'm searching for. Not all divs and p tags have classes, let alone them being unique (no other elements with the same classname). You're solution assumes a class is available on that element. – Ralph Jul 29 '19 at 16:00
  • But you can access each one of them using $(document).on('mouseenter mouseleave', '.sj-highlight', function (e) {}); No? Because that's what i assumed from your code above. – Abdelhak Elbouadi Jul 29 '19 at 16:05
  • Yes i can access them right then and there, but i need to store something to a database to target that element later. And if the element doesnt have a (unique) class or id i can't target it. That's why i need something else. – Ralph Jul 29 '19 at 16:11
0

Here is an option that I used when trying to target elements without the ID or Class. You first need to figure out what each of these highlighted elements have in common. Either it be a specific color, element hierarchy, etc. Then you could use the filter() jquery to find all elements with that spec. This is what I used.

/*select an element that contains this piece of code your trying to target*/
$('#Parent_container').filter(function() {
  /*here you will specify what you're trying to identify or target*/
  return $(this).find('div[class="sj-highlight"]').length >0; 
   /*optional but you can create a condition to add code or do whatever you want*/
}).find('div[class="sj-highlight"]').after('<p>some stuff</p>');

Hope that helps. It might give you some idea of what options you have.

Vick
  • 43
  • 8
  • Hi Victor, the sj-highlight class is not available on the pages of our customer. – Ralph Jul 29 '19 at 18:12
  • 1
    Thing is, you can replace that with a specification like .find('div').has('a:contains("example text")') or something like that. Take a look at this documentation. It contains all of the jquery that selects/targets stuff https://api.jquery.com/category/selectors/ – Vick Jul 30 '19 at 12:44