How to display a single object from response.data? - javascript

Foloowing is my controller for displaying single book details from collection of json records
.controller('BookDetailsController', ['$scope','$http','$stateParams',function($scope,$http,$stateParams){
$http({
url: "/api/books/",
method: "get",
params: {id: $stateParams.id}
}).then(function(response){
$scope.books = response.data;
console.log($scope.books);
})
}]);
<div class="panel panel-default">
<div class="panel-heading">Online Bookstore</div>
<div class="panel-body">
<div class="col-md-12">
<div class="col-md-3">
<img src="{{book.imgUrl}}" class="img-thumbnail" width="200" height="200">
</div>
<div class="col-md-9">
<h2>{{book.title}}</h2>
<p style="text-align:justify;">{{book.description}}</p>
</div>
</div>
<hr>
</div>
</div>
How to display single book record from response.data; using above controller

If $scope.books is an array, you can
1) Loop over the array to display all books
<div ng-repeat="b in books">
{{b.title}}
<img ng-src="{{b.imgUrl}}"
...
</div>
2) Display only one book from its position in the array
<h1>First book</h1>
{{books[0].title}}
<img ng-src="{{books[0].imgUrl}}"/>

Just take the first object inside the data,
$scope.book = response.data[0];

Loop through the books in the outer <div>:
....
<div class="col-md-12" ng-repeat="book in books">
....
To display a single record (say for index 0), simple use books[0] in the view:
..
<img src="{{books[0].imgUrl}}" class="img-thumbnail" width="200" height="200">
</div>
<div class="col-md-9">
<h2>{{books[0].title}}</h2>
<p style="text-align:justify;">{{books[0].description}}</p>
</div>

if $scope.books is an array then you can use the ng-repeat as the above code by #mistails. it will simply create an list of books dynamically . and from the list you can select particular book and you can pass the id to fetch the book's whole data.
<div ng-repeat="b in books" data-ng-click="showBookData(b)">
{{b.title}}
<img ng-src="{{b.imgUrl}}"
...
</div>
showBookData()
on the click you can open a modal and show the total details.

Related

Jquery: foreach through html block elements

I have html blocks and there would be many this kind of html block with different html values and image sources.
<div class="customers__photo" data-id="a1">
<div class="infoblock infoblock-hidden">
<div class="infoblock__user-name"><strong>Alexander</strong></div>
<div class="infoblock__date">21 August 2022</div>
<div class="infoblock__text">Comportable table</div>
</div>
<img src="girl1.jpg" class="reviews__photo">
</div>
I want to extract all html values as array and I will console.log all values, sources with Jquery.
img_array =$(this).closest('.customers__content').find('.infoblock__user-name, .infoblock__date, .infoblock__text, img').map(function() {return
let name = $(".infoblock__user-name").html();
let date = $(".infoblock__date").html();
let text = $(".infoblock__text").html();
$("img").attr("src")
}).get();
img_array.forEach(function(name, date, text, src) {
console.log(name, date, text, src);
//$(".listblock").append(<img class="listblock__photo" src="${src}">);
});
I want to get all class values as i got for source of image (for (infoblock__user-name, infoblock__date, infoblock__text, )) using one foreACH. PLEASE HOW CAN i do that?
Your syntax to implement map() isn't correct. You need to return an object, and the properties of that object need to be key/value pairs.
You also need to retrieve the values from the DOM relative to the current .customers__photo element in the DOM, not by selecting all instances of that class.
Try this:
const data = $('.customers__photo').map((i, el) => ({
name: $(el).find('.infoblock__user-name').text(),
date: $(el).find('.infoblock__date').text(),
text: $(el).find('.infoblock__text').text(),
src: $(el).find('.reviews__photo').prop('src'),
})).get();
console.log(data);
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.6.1/jquery.min.js"></script>
<div class="customers__photo" data-id="a1">
<div class="infoblock infoblock-hidden">
<div class="infoblock__user-name"><strong>Alexander</strong></div>
<div class="infoblock__date">21 August 2022</div>
<div class="infoblock__text">Comportable table</div>
</div>
<img src="girl1.jpg" class="reviews__photo">
</div>
<div class="customers__photo" data-id="a1">
<div class="infoblock infoblock-hidden">
<div class="infoblock__user-name"><strong>John</strong></div>
<div class="infoblock__date">22 August 2022</div>
<div class="infoblock__text">Expandable table</div>
</div>
<img src="girl2.jpg" class="reviews__photo">
</div>
<div class="customers__photo" data-id="a1">
<div class="infoblock infoblock-hidden">
<div class="infoblock__user-name"><strong>Edward</strong></div>
<div class="infoblock__date">23 August 2022</div>
<div class="infoblock__text">Collapsable table</div>
</div>
<img src="girl3.jpg" class="reviews__photo">
</div>

Adding join() to a map() function

I'm mapping over an array to display data in the browser using template literals.
With each rendered object, a comma shows up in the browser and also when I inspected the element. I did some reading and I think it is because I haven't joined the array, which I am trying to do but I am not understanding where to add it in the basic function I have.
Here is the code:
let synopsisRender = synopsisContent.map((item)=>{
return`
<div class="synopsis" key=${item.id}>
<div class="synopsisHeader">
<div class="cover">
<img src="${item.poster}" alt="${item.altText}">
</div>
<div class="synopsisTitle">
<h1>${item.title}</h1>
</div>
</div>
<div class="synopsisText">
<h2>${item.subTitle}</h2>
<p>${item.synopsisText}</p>
</div>
</div>
`
});
document.getElementById("synopsis").innerHTML = synopsisRender;
After mapping, but before assigning to innerHTML.
let synopsisRender = synopsisContent.map((item)=>{
return`
<div class="synopsis" key=${item.id}>
<div class="synopsisHeader">
<div class="cover">
<img src="${item.poster}" alt="${item.altText}">
</div>
<div class="synopsisTitle">
<h1>${item.title}</h1>
</div>
</div>
<div class="synopsisText">
<h2>${item.subTitle}</h2>
<p>${item.synopsisText}</p>
</div>
</div>
`
}).join(''); //Here...
document.getElementById("synopsis").innerHTML = synopsisRender; //...Or here, `synopsisRender.join('')`

Unable to filter data from database due to laravel blade curly braces "{{ }}"

I'm trying to filter data gotten from database with the class="data-groups".
Here is the code:
this.shuffle.filter(function(element, shuffle) {
// If there is a current filter applied, ignore elements that don't match it.
if (shuffle.group !== Shuffle.ALL_ITEMS) {
// Get the item's groups.
var groups = JSON.parse(element.getAttribute('data-groups'));
var isElementInCurrentGroup = groups.indexOf(shuffle.group) !== -1;
// Only search elements in the current group
if (!isElementInCurrentGroup) {
return false;
}
}
var titleElement = element.querySelector('.book-item_title');
var titleText = titleElement.textContent.toLowerCase().trim();
return titleText.indexOf(searchText) !== -1;
});
};
<!-- begin snippet: js hide: false console: true babel: false -->
<div class="grid-shuffle">
<ul id="grid" class="row">
#foreach($libraries as $library)
<li class="book-item small-12 medium-6 columns" data-groups='["{{$library->genre}}"]' data-date-created='{{$library->published}}' data-title='{{ $library->title }}' data-color='{{$library->color}}'>
<div class="bk-img">
<div class="bk-wrapper">
<div class="bk-book bk-bookdefault">
<div class="bk-front">
<div class="bk-cover" style="background-image: url('img/001-small.png')"></div>
</div>
<div class="bk-back"></div>
<div class="bk-left"></div>
</div>
</div>
</div>
<div class="item-details">
<h3 class="book-item_title">{{$library->title}}</h3>
<p class="author">{{$library->author}} • {{$library->published}}</p>
<p>{{$library->synopsis}}</p>
Details
</div>
<div class="overlay-details">
Close
<div class="overlay-image">
<img src="img/001.jpg" alt="Book Cover">
<div class="back-color"></div>
</div>
<div class="overlay-desc activated">
<h2 class="overlay_title">{{$library->title}}</h2>
<p class="author">by {{$library->author}}</p>
<p class="published">{{$library->published}}</p>
<p class="synopsis">{{ $library->synopsis }}</p>
Preview
</div>
<div class="overlay-preview">
Back
<h4 class="preview-title">Preview</h4>
<div class="preview-content">
<h5>Chapter 1</h5>
<p>{{$library->details}}</p>
</div>
</div>
</div>
</li>
#endforeach
</ul>
</div>
The problem is it doesn't work unless I hard code the genre like this
data-groups='["fiction"]'
Now since I'm retrieving data from a database using the foreach loop it means any book out the database is automatically given the "fiction" attribute regardless of its db assigned genre.
Any help on how to solve this will be appreciated.
Found the problem
I was Filtering with this lines of code
All Categories
Fantasy
Sci-Fi
Classics
Fairy Tale
The problem was that the data-group items are case sensitive. So for example I was filtering with "classic" while my database was providing "Classic" therefore making the filter function seem faulty.

Get element text through GTM Custom JavaScript Variable

I have two groups of links all with the same class names, the only difference is the text in the .
I need to get the text for the clicked link and pass it to GA through GTM.
<div class="item-set">
<header>Section Title One</header>
<section class="products">
<div class="list">
<img src="/ProductImages1.jpg">
</div>
<div class="list">
<img src="/ProductImages2.jpg">
</div>
<div class="list">
<img src="/ProductImages3.jpg">
</div>
</section>
</div>
<div class="item-set">
<header>Section Title Two</header>
<section class="products">
<div class="list">
<img src="/ProductImages1.jpg">
</div>
<div class="list">
<img src="/ProductImages2.jpg">
</div>
<div class="list">
<img src="/ProductImages3.jpg">
</div>
</section>
</div>
I have created a custom javascript variable
function() {
$('section.products div.list').click(function() {
return $(this).closest('.item-set').find('header').text();
});
}
But the bleep thing isn't working as I expect (or at all). It returns "undefined".
Any assistance is greatly appreciated.
You shouldn't bind to click event in JS variable. You should use JS variables in GTM only for receiving values
The correct way to achieve your goal is:
1) Enable built-in variable Click Element (if you already have it, you can skip this step)
2) Create trigger, which will fire when you clicking on your links
CSS selector on the screenshot is .item-set .list a
3) Create JS variable
Code is: function() {
return $({{Click Element}}.closest('.item-set')).find('header').text();
}
3) Create a tag, which will send data to GA
Here you can use your variable form step 3 {{Click List Header}}
Maybe you are not capturing/storing the return $(this).closest('.item-set').find('header').text(); from the function?
When you for example immediately invoke your function and click a div, the text of the <header> will be logged to the console.
(function() {
$('section.products div.list').click(function(e) {
e.preventDefault(); // to prevent the default action of the click
console.log($(this).closest('.item-set').find('header').text());
return $(this).closest('.item-set').find('header').text();
});
})();
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="item-set">
<header>Section Title One</header>
<section class="products">
<div class="list">
<img src="/ProductImages1.jpg">
</div>
<div class="list">
<img src="/ProductImages2.jpg">
</div>
<div class="list">
<img src="/ProductImages3.jpg">
</div>
</section>
</div>
<div class="item-set">
<header>Section Title Two</header>
<section class="products">
<div class="list">
<img src="/ProductImages1.jpg">
</div>
<div class="list">
<img src="/ProductImages2.jpg">
</div>
<div class="list">
<img src="/ProductImages3.jpg">
</div>
</section>
</div>

Angular JS binding working only once in the page

I have a page where I do multiple binding to the same object (item, item2, message, messageType)
Though I placed the binding in several part of the page it works only the first time i placed. The objects are filled with ajax calls that return correctly the value (I logged them in the console)
What sounds even strange to me is that the <infomessage> directive has been used in several other places in the app (twice in the same page) and worked perfectly.
Do you have any idea on why these bindings don't work?
I even tried to $watch the objects and they are properly changes but seems that the view use the updated value only the first time
<div class="container" ng-app="MyApp" >
<div class="row" ng-controller="MyCtrl" >
<div class="col-lg-10">
<h3>...</h3>
</div>
<div class="col-lg-10">
<infomessage type="{{messageType}}" message="{{message}}"></infomessage>
</div>
<div class="col-lg-10">
Item: {{item.idbene_ext}} / {{item.id}} / {{item.img}}<br>
Ubicazione: {{item2.id}} {{item2.code}}
</div>
</div>
<div class="row" style="margin-top:20px">
<div class="col-xs-1"></div>
<div class="col-xs-4" ng-class="{'ubiBox':true,'ausilio-enabled':(item!=null),'ausilio-disabled':(item==null), 'boxfocus':(item==null)}">
<div ng-show="item==null">
<div class="number">1</div>
<img src="assets/images/disabled-128.png" width="100" class="img_none"/>
<h4> {{item.idbene_ext}} Select an item</h4>
</div>
<div ng-show="ausilio!=null">
<h4>Item:{{item.idbene_ext}}</h4>
</div>
</div>
<div class="col-xs-2"></div>
<div class="col-xs-4" ng-class="{'ubiBox':true,'ubi-enabled':(item!=null),'ubi-disabled':(item==null),'boxfocus':(item!=null) }">
<div ng-show="item==null">
<div class="number">2</div>
<img src="assets/images/Office-disabled-128.png" width="100" class="img_none"/>
<h4> Select the second item</h4>
</div>
<div ng-show="item!=null">
<h4>Item2 {{item2.code}}</h4>
</div>
</div>
<div class="col-xs-1"></div>
</div>
<div class="row">
<div class="col-lg-10">
<infomessage type="{{messageType}}" message="{{message}}"></infomessage>
</div>
<div class="col-lg-10">
Item: {{item.idbene_ext}} / {{item.id}} / {{item.img}}<br>
Ubicazione: {{item2.id}} {{item2.code}}
</div>
</div>
Here's the angularJS code
MyApp.controller("MyCtrl",function($scope,$http,Config,BarcodeService){
$scope.iditem2=-1
$scope.iditem=-1
$scope.item2=null
$scope.item=null
$scope.message=""
$scope.messageType=""
$scope.$on(BarcodeService.handleitem2,function(){
$scope.message=""
$scope.messageType=""
if($scope.item==null){
$scope.message="select an item before"
$scope.messageType="error"
}
$scope.iditem2=BarcodeService.id
$http
.post(Config.aj,{call:"item2.getitem2",id:$scope.iditem2})
.success(function(data){
$scope.item2=data.payload
})
})
$scope.$watch("item",function(){
console.log("---->",$scope.item)
},true)
$scope.$on(BarcodeService.handleitem,function(){
$scope.message="loading item"
$scope.messageType="info"
$scope.iditem=BarcodeService.id
$http
.post(Config.aj,{call:"item.getArticoloByIdMin",id:BarcodeService.id})
.success(function(data){
$scope.message="item loaded!!"
$scope.item=data.payload
})
})
})
Ok guys, got it!
The problem was lying in the fact that I have two in my application but i placed the ng-controller only on the first one.
This caused all the binding in the second div to fail because they were outside the controller.
I moved the ng-controller in the parent div that contains both and now everything works like a charm.
Thanks anyway to #wachme and #ivarni for taking care of my question.
Happy coding to *

Categories