Get elements between 2 elements - javascript

I have this html:
<div class="categories">
<div class="list-group">
<a class="root list-group-item" id="427" style="display: block;"><span class="glyphicon indent0 glyphicon-chevron-down"></span><span>Home</span></a>
<a class="list-group-item first active" id="428" style="display: block;"><span class="glyphicon indent1 glyphicon-chevron-right"></span><span>Images</span></a>
<a class="list-group-item child" id="431" style="display: none;"><span class="glyphicon indent2"></span><span>Sub category</span></a>
<a class="list-group-item first" id="429" style="display: block;"><span class="glyphicon indent1 glyphicon-chevron-right"></span><span>Videos</span></a>
<a class="list-group-item child" id="432" style="display: none;"><span class="glyphicon indent2"></span><span>Another sub</span></a>
<a class="list-group-item first" id="430" style="display: block;"><span class="glyphicon indent1"></span><span>Documents</span></a>
</div>
</div>
and what I need to do is select all elements between a.active.
To explain that a little better; a.active has a span.glyphicon with the class indent1, so I need to select the elements between indent1 and the next indent1
I attempted to use jQuery's nextAll function but couldn't get it to work correctly :(
any help would be appreciated,
/r3plica
Update 1
Thanks to Arun, here is my script which now works:
$(".glyphicon", treeRoot).on('click', function (e) {
e.stopPropagation();
var $glyph = $(this);
var $item = $glyph.parent();
var indent = $item.find(".glyphicon").prop('className').match(/\b(indent\d+)\b/)[1];
console.log($item[0].outerHTML);
console.log(indent);
if (indent != undefined) {
var $children = $item.nextUntil("a:has(." + indent + ")");
console.log($children[0].outerHTML);
if ($glyph.hasClass("glyphicon-chevron-right")) {
$glyph
.addClass('glyphicon-chevron-down')
.removeClass("glyphicon-chevron-right");
if ($children != null) $children.show();
} else {
$glyph
.addClass('glyphicon-chevron-right')
.removeClass("glyphicon-chevron-down");
if ($children != null) $children.hide();
}
}
});

Try
$('.active').nextUntil('a:has(.indent1)')
To dynamically determine the indent value
var $active = $('.active');
var indent = $active.find('.glyphicon').prop('className').match(/\b(indent\d+)\b/)[1];
var $nexts = $active.nextUntil('a:has(.' + indent + ')');
console.log($nexts)
Demo: Fiddle

Try using nextUntil()
Live Demo
$('.active:has(.indent1)').nextUntil(':has(.indent1)')

Maybe with nextUntil (from Jquery)
Look at http://api.jquery.com/nextUntil/
$('.active').nextUntil('.indent1');

Related

JQuery create chat tab by clicking on contact from contact list

I'd love if you could help me out w/ this issue I'm having. I'm trying to create a list of contacts, like the following, and then be able to open a chat tab for that contact. Somehow,it seems like the JQuery isn´t working, I'd appreciate if you could give me a hand.
1st piece (HTML contact)
<div id="contact-list">
<div class="contact-line">
<button class="contact-name">111111111</button>
<div class="status"><div class="online"></div></div>
<div class="user-photo"></div>
<div class="unread-wrap"><div class="unread">2</div></div>
</div>
.....
</div>
<ul id="ConversationsHeaderList">
</ul>
2nd Piece (JQuery)
<script type="text/javascript">
$('.contact-name').click( function() {
var $chatHeaderContent1 = $(this).parent().html();
var $chatHeaderContent2 = $chatHeaderContent1 + '<button class="ConversationClose" title="Close Conversation"><i class="fa fa-window-close" aria-hidden="true"></i></button>';
$('#ConversationsHeaderList').append($chatHeaderContent2);
});
</script>
Somehow, I can´t make it create something like this:
<ul id="ConversationsHeaderList">
<li class="ConversationsHeader">
<button class="contact-name">Friend 1</button>
<div class="status"><div class="online"></div></div>
<div class="user-photo"></div>
<div class="unread-wrap"><div class="unread">1</div></div>
<button class="ConversationClose" title="Close Conversation"><i class="fa fa-window-close" aria-hidden="true"></i></button>
</li>
</ul>
Try this, you just have to wrap the content in li element
<script type="text/javascript">
$('.contact-name').click( function() {
var $chatHeaderContent1 = $(this).parent().html();
var $chatHeaderContent2 = '<li class="ConversationsHeader">' + $chatHeaderContent1 + '<button class="ConversationClose" title="Close Conversation"><i class="fa fa-window-close" aria-hidden="true"></i></button>' + '</li>';
$('#ConversationsHeaderList').append($chatHeaderContent2);
});
</script>

Selecting a certain dropdown element using xpath (or better alternative)

How would I select a certain element in this drop down list.
<li role="presentation" ng-repeat="match in $matches" ng-class="{active: $isActive($index)}" class="ng-scope active">
<a style="cursor: default" role="menuitem" tabindex="-1" ng-click="$select($index, $event)">
<!-- ngIf: $isMultiple && $isActive($index) -->
<i class="glyphicon glyphicon-ok pull-right" ng-if="$isMultiple && $isActive($index)"></i>
<!-- end ngIf: $isMultiple && $isActive($index) -->
<span ng-bind="match.label" class="ng-binding">Streamer</span>
</a>
</li>
I tried this
element(by.model('selectedAvailable')).click();
element(by.xpath('..//ul//li[1]')).click().
and this:
element(by.repeater('match in $matches').row(0)).click();
An alternative would be to use by.cssContainingText :
element(by.cssContainingText('[ng-repeat="match in $matches"]', 'Streamer')).click();
I would filter() it, assuming you know the "Streamer" label and want to select it:
var matches = element.all(by.repeater('match in $matches'));
matches.filter(function (match) {
return match.element(by.binding("match.label")).getText().then(function (text) {
return text === "Streamer";
});
}).first().click();
Or, in a similar fashion with evaluate() instead of getText():
var matches = element(by.repeater('match in $matches'));
matches.filter(function (match) {
return match.evaluate("match.label").then(function (label) {
return label === "Streamer";
});
}).first().click();

MVC javascript display selected data

First of all, I list the e-mail from coming ActionResult in the first cycle.
I want to see the details by clicking on the listed data. I open with the help of jQuery details. The problem arises in this section. in this case ,the opening of the details of the first mail in the detail of each row.
There are details of the message in the second loop.To connect to the two loops in a guid font was coming. (MessageId).
id=messageId (guid type)
mailing list
<div class="message-list-container">
<div class="message-list" id="message-list">
#foreach (var item in Model)
{
<div id="#item.MessageId" class="message-item">
<span class="sender" title="#item.From">
#item.From
</span>
<span class="time">#mvcHelper.saatAyarla(item.Date)</span>
#if(item.Attachments.Any())
{
<span class="attachment">
<i class="ace-icon fa fa-paperclip"></i>
</span>
}
<span class="summary">
<span class="text">
#item.Subject
</span>
</span>
</div>
}
</div>
</div>
mailing details
<!--Messsage details-->
#foreach (var item in Model)
{
<!-- <div class="hide message-content" id="id-message-content">-->
<div class="hide message-content" id="#item.MessageId">
<div class="message-header clearfix">
<div class="pull-left">
<span class="blue bigger-125"> #item.Subject </span>
<div class="space-4"></div>
<i class="ace-icon fa fa-star orange2"></i>
<img class="middle" alt="John's Avatar" src="/Areas/admin/Content/images/avatars/avatar.png" width="32" />
#item.From
<i class="ace-icon fa fa-clock-o bigger-110 orange middle"></i>
<span class="time grey">#mvcHelper.saatGoster(item.Date)</span>
</div>
</div>
<div class="hr hr-double"></div>
<div class="message-body">
<p>
#item.TextBody
</p>
</div>
<div class="hr hr-double"></div>
<!--Eklenti paneli-->
<div class="message-attachment clearfix">
#if (item.Attachments.Any())
{
<div class="attachment-title">
<span class="blue bolder bigger-110">Eklentiler</span>
<span class="grey">(#item.Attachments.Count() Dosya)</span>
</div>
<ul class="attachment-list pull-left list-unstyled">
#foreach (var attachment in item.Attachments)
{
<li>
<a href="#" class="attached-file">
<i class="ace-icon fa fa-file-o bigger-110"></i>
<span class="attached-name">#mvcHelper.getAttachmentName(attachment.ToString())</span>
</a>
<span class="action-buttons">
<a href="#">
<i class="ace-icon fa fa-download bigger-125 blue"></i>
</a>
<a href="#">
<i class="ace-icon fa fa-trash-o bigger-125 red"></i>
</a>
</span>
</li>
}
</ul>
}
</div>
</div><!-- /.message-content -->
}
<!--Eklenti paneli Son-->
<!--message details end-->
loop connecting two points.
first foreach = <div id="#item.MessageId" class="message-item">
//Places where the problem is. They need to be connected.
second foreach = <!-- <div class="hide message-content" id="id-message-content">-->
<div class="hide message-content" id="#item.MessageId">
var content = message.find('.message-content:last').html($('#id-message-content').html());
jQuery code
$('.message-list .message-item .text').on('click', function () {
var message = $(this).closest('.message-item');
//if message is open, then close it
if (message.hasClass('message-inline-open')) {
message.removeClass('message-inline-open').find('.message-content').remove();
return;
}
$('.message-container').append('<div class="message-loading-overlay"><i class="fa-spin ace-icon fa fa-spinner orange2 bigger-160"></i></div>');
setTimeout(function () {
$('.message-container').find('.message-loading-overlay').remove();
message
.addClass('message-inline-open')
.append('<div class="message-content" />');
var content = message.find('.message-content:last').html($('#id-message-content').html());
//remove scrollbar elements
content.find('.scroll-track').remove();
content.find('.scroll-content').children().unwrap();
content.find('.message-body').ace_scroll({
size: 150,
mouseWheelLock: true,
styleClass: 'scroll-visible'
});
}, 500 + parseInt(Math.random() * 500));
});
Your first problem is that you are creating multiple elements with identical id properties. This makes your HTML invalid.
Here is the problem code:
#foreach (var item in Model)
{
<div id="#item.MessageId" class="message-item">
...
#foreach (var item in Model)
{
<div class="hide message-content" id="#item.MessageId">
...
For each message in your model, this will create 2 <div> elements whose id has the value of the #item.MessageID variable. The second of these is and illegal element because it has the same ID as an earlier element. You will need to make these <div>s have unique IDs.
The second problem is:
When you run
var content = message.find('.message-content:last').html($('#id-message-content').html());
this part:
$('#id-message-content').html()
cannot find anything because there is no element whose id is "id-message-content". Also every time you open the message, you are appending another "message-content" div into the message-item. This is not necessary.
To fix these issues, you can change the code like this:
First loop:
#foreach (var item in Model)
{
<div data-messageid="#item.MessageId" class="message-item">
...
<span class="summary">
<span class="text">
#item.Subject
</span>
</span>
<div class="message-content" hidden></div>
...
Second loop:
#foreach (var item in Model)
{
<div class="hide message-content" id="message-content-#item.MessageId">
...
jQuery:
$('.message-list .message-item .text').on('click', function () {
var message = $(this).parents('.message-item');
//if message is open, then close it
if (message.hasClass('message-inline-open')) {
message.removeClass('message-inline-open').find('.message-content').hide();
return;
}
$('.message-container').append('<div class="message-loading-overlay"><i class="fa-spin ace-icon fa fa-spinner orange2 bigger-160"></i></div>');
setTimeout(function () {
$('.message-container').find('.message-loading-overlay').remove();
message.addClass('message-inline-open');
var content = message.find(".message-content");
content.show();
content.html($('#message-content-' + message.data("messageid")).html());
//remove scrollbar elements
content.find('.scroll-track').remove();
content.find('.scroll-content').children().unwrap();
content.find('.message-body').ace_scroll({
size: 150,
mouseWheelLock: true,
styleClass: 'scroll-visible'
});
}, 500 + parseInt(Math.random() * 500));
});
Solved
public static class mvcHelper
{
public static string variableReplace(string id)
{
string yazi = null;
if (id != null)
{
yazi = id.Replace('#', 'a').ToString();
}
else
{
yazi = id;
}
return yazi;
}
}
<div data-messageid="#mvcHelper.variableReplace(item.MessageId)" class="message-item">
<div class="hide message-content" id="message-content-#mvcHelper.variableReplace(item.MessageId)">

hover over one element and addClass to other elem in Angular JS

Attempting with the below jQuery method: But this does not work in my Angular environment, assuming because I'm attempting to do this outside of angular JS scope methods, but I don't know how to implement this using Angular scope methods (new to angular) any advice?
$('.song-thumb .hover-play').on('mouseenter', function(e) {
var elem = $('section.suggestedAlbums img');
elem.trigger(e.type);
elem.addClass('hoverclass');
});
$('.song-thumb .hover-play').on('mouseleave', function(e) {
var elem = $('section.suggestedAlbums img');
elem.trigger(e.type);
elem.removeClass('hoverclass');
});
var count = 0;
$('section.suggestedAlbums img').hover(function() {
count++;
$('[remove]').html('<label remove><br>It triggers the hover event(' + count + ') too.<br></label>');
});
Full page code:
<script>
$('.song-thumb .hover-play').on('mouseenter', function(e) {
var elem = $('section.suggestedAlbums img');
elem.trigger(e.type);
elem.addClass('hoverclass');
});
$('.song-thumb .hover-play').on('mouseleave', function(e) {
var elem = $('section.suggestedAlbums img');
elem.trigger(e.type);
elem.removeClass('hoverclass');
});
var count = 0;
$('section.suggestedAlbums img').hover(function() {
count++;
$('[remove]').html('<label remove><br>It triggers the hover event(' + count + ') too.<br></label>');
});
</script>
<!-- <h2>{{trackListData.listTitle}}</h2>
--><div ng-repeat="track in trackListData.tracks track by $index " class="feature-item-homepage fade-animate-nostagger">
<div class="song-thumb" ng-class="{active: $root.currentPlaying.song_id == track.id}">
<!--3 Cases-->
<!--Not the song being played-->
<div class="hover-play" ng-if="$root.currentPlaying.song_id != track.id" ng-click="$root.playSong(track);">
<i class="fa fa-plus add-to-playlist" ng-init="playlistOption = false" ng-click="$root.initPlaylistOption($event, track.id); $event.stopPropagation();"></i>
<i class="fa fa-play play-song"></i>
<img src="img/producer_icon_white.png" class="prod_logo">
<div class="song-title" style="width: 80%;padding-top:25px;">
<a class="song-linking" href="#/song/{{track.id}}">
<h4>{{track.title}}</h4>
<h5>{{track.artist.user_name}}</h5>
</a>
</div>
</div>
<!--The current song but paused-->
<div class="hover-play" ng-if="$root.currentPlaying.song_id == track.id && !$root.isPlaying" play-music>
<i class="fa fa-plus add-to-playlist" ng-init="playlistOption = false" ng-click="$root.initPlaylistOption($event, track.id); $event.stopPropagation();"></i>
<i class="fa fa-play play-song"></i>
</div>
<!--The current song but playing-->
<div class="hover-play" ng-if="$root.currentPlaying.song_id == track.id && $root.isPlaying" pause-music>
<i class="fa fa-plus add-to-playlist" ng-init="playlistOption = false" ng-click="$root.initPlaylistOption($event, track.id); $event.stopPropagation();"></i>
<i class="fa fa-pause pause-song"></i>
</div>
<img ng-src="{{(track.albums[0].album_picture? $root.fileServer +'uploads/' + track.albums[0].album_picture:(track.artist.profile_picture? $root.fileServer +'uploads/' + track.artist.profile_picture:'img/defaultalbum.png'))}}" />
</div>
<!-- <div class="song-title-wrap">
<div class="song-title">
<a class="song-linking" href="#/song/{{track.id}}">
<h4>{{track.title}}</h4>
<h5>{{track.artist.user_name}}</h5>
</a>
</div>
</div> -->
</div>
Add a controller to a containing div:
<div ng-controller='MyController'>
Add ngMouseleave and ngMouseenter to the .song-thumb .hover-play element
<div class="hover-play" ng-if="$root.currentPlaying.song_id != track.id" ng-click="$root.playSong(track);" ng-mouseenter='state.hoverPlay=true;' ng-mouseleave='state.hoverPlay=false'>
Add the controller
angular.controller('MyController', [ '$scope', function ($scope) {
$scope.state = {
hoverPlay: false
};
}]);
Use ngClass to add/remove the class
<img ng-class="{ 'hoverclass': state.hoverPlay }" . . . >

Changing multiple images with JQuery

So here is the JQuery I am using
jQuery(document).ready(function($) {
$('.ltwitch').each(function () {
var tnick = $(this).data('tnick');
var span = $(this).next();
$.getJSON("https://api.twitch.tv/kraken/streams/"+tnick+".json?callback=?", function(c) {
if (c.stream == null) {
span.html("Offline");
} else {
span.html("Online");
}
});
});
});
And the HTML that was with it when I found it
<a class="ltwitch" href="http://www.twitch.tv/ifstudios" data-tnick="IFStudios">IFStudios</a> (<span>...</span>)
RoosterTeeth (...)
Now what I want to do, I have HTML that looks like this
<a href="#portfolioModal3" class="portfolio-link" data-toggle="modal">
<div class="portfolio-hover">
<div class="portfolio-hover-content">
<i class="fa fa-plus fa-3x"></i>
</div>
</div>
<img src="img/portfolio/sweet.png" class="img-responsive" alt="">
</a>
Basically when a channel becomes live I want to switch the img src from the image I have it set to, to the same image with -online on the end. So I can have multiple pictures on the website, but I can have the images change dependent on who is live and who isn't.
So if I have
<a href="#portfolioModal3" class="portfolio-link" data-toggle="modal">
<div class="portfolio-hover">
<div class="portfolio-hover-content">
<i class="fa fa-plus fa-3x"></i>
</div>
</div>
<img src="img/portfolio/sweet.png" class="img-responsive" alt="">
</a>
When her channel goes live, it will turn to
<a href="#portfolioModal3" class="portfolio-link" data-toggle="modal">
<div class="portfolio-hover">
<div class="portfolio-hover-content">
<i class="fa fa-plus fa-3x"></i>
</div>
</div>
<img src="img/portfolio/sweet-online.png" class="img-responsive" alt="">
Or if it was
<img src="img/portfolio/carrot.png"
it would turn to
<img src="img/portfolio/carrot-online.png"
Any ideas?
Try the below code
jQuery(document).ready(function($) {
$('.ltwitch').each(function () {
var tnick = $(this).data('tnick');
var span = $(this).next();
$.getJSON("https://api.twitch.tv/kraken/streams/"+tnick+".json?callback=?", function(c) {
var img = $(img-selector);
var source = img.attr('src');
if (c.stream != null) {
// Online
if(source.indexOf('.png') != -1){
source = source.replace(".png", "-online.png");
img.attr('src',source);
}
}
else{
// Offline
source.replace("-online", "");
img.attr('src',source);
}
});
});
});
Note: You have to pass the correct image selector to $(img-selector). Also call the same function again for refreshing

Categories