Reloading new data into a 5 starts rating system - javascript

I have an autoload_process.php file where I retrieve info from my data base and I print it. One of the info I retrieve and print is the rating. I also have in this file my script to print the rating.
<script type="text/javascript">
$(function() {
$('span.stars').stars();
});
$.fn.stars = function() {
return $(this).each(function() {
$(this).html($('<span />').width(Math.max(0, (Math.min(5, parseFloat($(this).html())))) * 16));
});
}
</script>
//Provide the group that is going to be load
$group_number = filter_var($_POST["group_no"], FILTER_SANITIZE_NUMBER_INT, FILTER_FLAG_STRIP_HIGH);
// To show 3 results at a time
$items_per_group = 3;
//get current starting point of records
$position = ($group_number * $items_per_group);
$city = filter_var($_POST["nameofcity"]);
//Limit our results within a specified range.
$db = pg_connect("$db_host $db_name $db_username $db_password");
$query = "SELECT * FROM menu where city='$city' ORDER BY rating DESC LIMIT $items_per_group OFFSET $position";
$rating = $myrow[rating];
echo '<span class="stars">';
echo $rating;
echo '</span>';
When the page is load for the first time everything works fine but the problem I have is that when I scroll all the way to the bottom and the page is reload with the new info the rating changes. It seams that everytime that a new set of data is loaded all the previous ratings are set to the Maximum or default value "5 Starts" (I'm guessing because the autoload.process.php file is run it again)
Example: (let's say that I load 3 results at a time)
First Load:
Hotel 1 --> Rating 5 (This is correct)
Hotel 2 --> Rating 4 (This is correct)
Hotel 3 --> Rating 3 (This is correct)
Now I get to the bottom of the page and the next info is loaded (second load):
Hotel 1 --> Rating 5 (This is INCORRECT) filled with default value (Hotel1)
Hotel 2 --> Rating 5 (This is INCORRECT) filled with default value (Hotel1)
Hotel 3 --> Rating 5 (This is INCORRECT) filled with default value (Hotel1)
Hotel 4 --> Rating 2 (This is correct)
Hotel 5 --> Rating 1 (This is correct)
Hotel 6 --> Rating 3 (This is correct)
Now I get to the bottom of the page and the next info is loaded (third load):
Hotel 1 --> Rating 5 (This is INCORRECT) filled with default value (Hotel1)
Hotel 2 --> Rating 5 (This is INCORRECT) filled with default value (Hotel1)
Hotel 3 --> Rating 5 (This is INCORRECT) filled with default value (Hotel1)
Hotel 4 --> Rating 5 (This is INCORRECT) filled with default value (Hotel1)
Hotel 5 --> Rating 5 (This is INCORRECT) filled with default value (Hotel1)
Hotel 6 --> Rating 5 (This is INCORRECT) filled with default value (Hotel1)
Hotel 7 --> Rating 3 (This is correct)
Hotel 8 --> Rating 2 (This is correct)
Hotel 9 --> Rating 1 (This is correct)
I think the issue is having this piece of code in the audtoload_process.php file
<script type="text/javascript">
$(function() {
$('span.stars').stars();
});
$.fn.stars = function() {
return $(this).each(function() {
$(this).html($('<span />').width(Math.max(0, (Math.min(5,parseFloat($(this).html())))) * 16));
});
}
</script>
Especially in this line of code:
$(this).html($('<span />').width(Math.max(0, (Math.min(5,parseFloat($(this).html())))) * 16));
Also If I change the value in: Math.min(5,parseFloat from 5 to 1, when the new data loads, the previous values change to 1 instead of 5. Like:
First Load:
Hotel 1 --> Rating 5 (This is correct)
Hotel 2 --> Rating 4 (This is correct)
Hotel 3 --> Rating 3 (This is correct)
Now I get to the bottom of the page and the next info is loaded (second load):
Hotel 1 --> Rating 1 (This is INCORRECT) filled with default value (Hotel1)
Hotel 2 --> Rating 1 (This is INCORRECT) filled with default value (Hotel1)
Hotel 3 --> Rating 1 (This is INCORRECT) filled with default value (Hotel1)
Hotel 4 --> Rating 2 (This is correct)
Hotel 5 --> Rating 1 (This is correct)
Hotel 6 --> Rating 3 (This is correct)
But if I don't include it there then the starts are not fill up and I see something like:(starts without being filled with the value in top of the starts)
This is what I see if I include the code (Which is what I suppose to see) but then I'm having the issue mentioned above.
Definition of the class Start:
<style>
span.stars, span.stars span {
display: block;
background: url(stars.png) 0 -16px repeat-x;
width: 80px;
height: 16px;
}
span.stars span {
background-position: 0 0;
}
</style>
Any help would be appreciated
UPDATE
This is what I see before to scroll down and autoload the new data. (As can be observed, the starts are fill up to the same value that indicated in the top of the picture.
This is after getting to the bottom of the page and doing the autoload. As it can be appreciated the the rating is still the same (3.11 and 2.89) in the top of the picture, so the actual value of the rating didn't change. All the other data associated didn't change either (as for example the number of ratings: 7 and 12) However, the only thing that it changes is the starts being fill up to max=5 and that's why I'm suspecting the issue is in this line of code
$(this).html($('<span />').width(Math.max(0, (Math.min(5,parseFloat($(this).html())))) * 16));
Or just having the script in the autoload_process.php file but I don't know how to solve the issue.

Looks like you are selecting all <span> elements each time you run your function, so your math is getting performed on both the newly added items as well as the old ones.
You could use an additional class name to identify spans that need updated. Then do your selection based off of that class.
Maybe something like this would work:
echo '<span class="stars notReadyYet">';
echo $rating;
echo '</span>';
.
$.fn.stars = function() {
return $(this).each(function() {
$(this).html($('.notReadyYet').width(Math.max(0, (Math.min(5,parseFloat($(this).html())))) * 16));
$(this).removeClass('notReadyYet'); //remove this class so it doesn't get processed again!
});
}

Related

Angular Devextreme - Get total number of rows on current page

In my Angular App, I have a requirement to display total number of rows on current page in pagination section. But currently Devextreme grid row count returns total row count irrespective of page.
Below is my code :-
<dxo-paging [pageSize]="5"> </dxo-paging>
<dxo-pager
[visible]="true"
[allowedPageSizes]="allowedPageSizes"
[displayMode]="displayMode"
[showPageSizeSelector]="showPageSizeSelector"
[showInfo]="true"
infoText="Displaying {0} - {2} of {1} "
[showNavigationButtons]="showNavButtons"
>
</dxo-pager>
Below screenshot :-
Now i have only 5 rows in the grid but it shows 11 which is the total row count which i have received from database. Please advise.
If i understand correctly, you want to show 1-5 on the first page, 6-10 on the second page and so on. You can achieve that by binding a function to the [infoText] property and customize the text output. This is not found in the official documentation but it works.
HTML:
<dxo-paging [pageSize]="5"> </dxo-paging>
<dxo-pager
[visible]="true"
[allowedPageSizes]="allowedPageSizes"
[displayMode]="displayMode"
[showPageSizeSelector]="showPageSizeSelector"
[showInfo]="true"
[infoText]="infoText"
[showNavigationButtons]="showNavButtons">
</dxo-pager>
JS/TS:
infoText(currentPageNumber, totalPageCount, totalRowCount) {
const myPageSize = 5; // use global variable instead and bind it to dxo-paging
const from = +currentPageNumber * myPageSize - (myPageSize - 1);
const to = +currentPageNumber * myPageSize;
return `Displaying ${from}-${to}`;
}

Javascript table cell highlighting in 3rd party application

I'm using Splunk version 7.0.1 and I'm trying to highlight my table cell colors based off of two other fields. Splunk has a sample to do this in Javascript that uses hardcoded values, but I need the values based off of a different field. I have the script working, but it randomly highlights some cells in the wrong color. I can't seem to figure out why.
The "Average Response Time" should be:
Red if the value is greater than or equal to the Threshold
Amber if the value is greater than or equal to the Objective but less than the Threshold
Green if the value is less than the Objective
My Table:
Transaction Count "Average Response Time" Objective Threshold
A/P - Close Module - FM1 1 7.52 2.00 6.00 **<-Colored Red and correctly**
...
A/P - Diagnosis- Run Search - FM1 2 4.01 100.00 100.00 **<- Colored Amber incorrectly**
Here is the dashboard source of the table:
<table id="response_time_highlight">
<title>NOTE: An Objective and/or Threshold of 100 indicates that an Objective and/or Threshold have not been identified for this particular transaction type.</title>
<search>
<query>index=arm sourcetype="arm:transaction" region="$region$" sitename="$sitename$" transaction_status IN ( $transaction_status$ ) username IN ( $username$ ) workstation_name IN ( $workstation_name$ ) transaction_name IN ( $transaction_name$ )
| stats count avg(response_time) AS response_time BY transaction_name objective threshold
| eval threshold=round(threshold,2)
| eval objective=round(objective,2)
| eval response_time=round(response_time,2)
| fields transaction_name count response_time objective threshold
| rename response_time AS "Average Response Time" transaction_name AS "Transaction Type" objective as Objective threshold as Threshold count as "Transaction Count"
| sort +transaction_name</query>
<earliest>$search_time.earliest$</earliest>
<latest>$search_time.latest$</latest>
<sampleRatio>1</sampleRatio>
</search>
<option name="count">20</option>
<option name="dataOverlayMode">none</option>
<option name="drilldown">none</option>
<option name="percentagesRow">false</option>
<option name="refresh.display">progressbar</option>
<option name="rowNumbers">true</option>
<option name="totalsRow">false</option>
<option name="wrap">true</option>
</table>
Here is the Javascript code (modified version of the dashboard examples one):
require([
'underscore',
'jquery',
'splunkjs/mvc',
'splunkjs/mvc/tableview',
'splunkjs/mvc/simplexml/ready!'
], function (_, $, mvc, TableView) {
var objective_value;
var threshold_value;
// Row Coloring Example with custom, client-side range interpretation
var CustomRangeRenderer = TableView.BaseCellRenderer.extend({
canRender: function (cell) {
// Enable this custom cell renderer for response_time field
return _(['Average Response Time', 'Objective', 'Threshold']).contains(cell.field);
},
render: function ($td, cell) {
// Add a class to the cell based on the returned value
var value = parseFloat(cell.value);
if (cell.field === 'Objective') {
objective_value = value;
}
if (cell.field === 'Threshold') {
threshold_value = value;
}
// Apply interpretation for number of historical searches
if (cell.field === 'Average Response Time') {
if (value >= threshold_value) {
$td.addClass('range-cell').addClass('range-severe');
}
else if (value >= objective_value) {
$td.addClass('range-cell').addClass('range-elevated');
}
else if (value < objective_value) {
$td.addClass('range-cell').addClass('range-low');
}
}
// Update the cell content
$td.text(value.toFixed(2)).addClass('numeric');
}
});
mvc.Components.get('response_time_highlight').getVisualization(function (tableView) {
// Add custom cell renderer, the table will re-render automatically.
tableView.addCellRenderer(new CustomRangeRenderer());
});
});
EDIT: Added a console.log to the javascript showing the output of each field. Noticed that the first row showing as undefined, and pushing the correct numbers down to the next row. Here is the output:
0 undefined undefined
8.64 100 100
7.52 2 6
0 2 6
7.52 2 6
1.11 10 25
2.28 2 6
2.92 2 6

How to add a message in cart for woocommerce based on item quantity

I have a unique business model where our pricing increases every 3 items meaning
1-3 items in cart = X cost
4-6 items = 2X cost
7-9 items = 3x cost
If a person has 1 or 2 items in the cart, I want them to know they can still add the difference from 3 to cart and pay the same price (get the most for their money). How do I do a check for total item quantity in cart and then display msg based on the quotient if not = 0?
If you need additional information, I will gladly provide as much as I can.
Thank you!
Attach a function upon page load or item selection which does just what you mentioned. I may have overcomplicated this, but tried to keep it as simple as possible. Use your existing 'add item' and onload functions:
var quantity = 0;
$(document).load(init());
function init()
{
quantity % 3 > 0 ? $('#quant').show() : $('#quant').hide();
$('#num').html(3 - (quantity % 3));
}
function addOne() // your buy function
{
quantity++;
init();
$('#total').html(quantity);
}
div#quant
{
width: 100%;
text-align: right;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="quant">Buy
<span id="num"></span>
more for free!
</div>
<br>
<button onclick="addOne()">Buy Item</button>
<h3>Total: <span id="total"></span></h3>

jade and java script - display element with condition

i am trying to display element only when the selling price is bigger than 0
this is my code
.basket-sidebar-right-body-basket-why-not-try
.item-grid-item(dynamic-position, data-rv-each-item='model:suggested', data-rv-on-click='view.attemptToAddItemToCart')
.item-title(data-rv-text='item.WebTitle | startCase')
.item-image(focusable)
img(focusable,data-rv-src='item.ImageUrl', onerror='this.src = "http://placehold.it/237x140";')
.why-not-try-text= strings.whyNotTry
.why-not-try-price
span.currency-symbol £
span.price(data-rv-text='item.SellingPrice | asCurrency')
i am trying to display the why not try price only when item.sellingPrice is bigger than 0
anyone know how i can do that
?

Loading specific div based on the results of multiple dropdowns

EDIT: Would the approach be much easier if the Javascript listed was removed completely, and the dropdown menus restyled as <div>'s within <li>'s, and the final div was generated by a Javascript onclick event? e.g.
<a id="click_link">click me</a>
$("#click_link").click(function(){
$('#div').load('http://www.link.com/');
});
Either way, the problem at hand...
My decision to use an elegant-looking javascript solution is highlighting my massive inexperience when it comes to javascript! The problem is, on the face of it, simple...
Once an option has been chosen on each of the dropdown menus, I need a final div to load so that a specific button can be shown (a link to buy the item with the specified options, e.g. choosing Necklace D, with Stone Option B, and Delivery Option A = loading div with 'Buy' Button #17)
The dropdowns are divs that are filled and styled through the Javascript (as opposed to using the simpler <form> and <input> method), giving the flexibility to add two lines of differently styled text for each option etc. - This is where I step into the realm of the unknown and my inexperience shines through.
The isolated section is viewable in its entirity here
Ok, to the code.
Here's the Javascript:
function createByJson() {
var pearlData = [
{description:'Choose your pearl...', value:'Pearls', text:'Pearls'},
{description:'Beautiful black stone', value:'Black Pearl', text:'Black Pearl'},
{description:'Classic white stone', value:'White Pearl', text:'White Pearl'}
];
$("#DropItPearls").msDropDown({byJson:{data:pearlData, name:'pearls', width: 200}}).data("dd");
var blodeuweddData = [
{description:'Choose your item...', value:'Blodeuwedd', text:'the Blodeuwedd Collection'},
{description:'A striking statement', value:'BlodeuweddCelticStatement', text:'Celtic Statement Piece'},
{description:'Gold laced flower and pearl', value:'BlodeuweddBracelet', text:'Bracelet'},
];
$("#DropItBlodeuwedd").msDropDown({byJson:{data:blodeuweddData, name:'blodeuwedd', width: 250}})
.msDropDown({on:{change:function(data, ui) {
var val = data.value;
if(val!="")
window.location = val;
}}}).data("dd");
var deliveryData = [
{description:'Choose your method...', value:'Delivery', text:'Delivery Options'},
{description:'4-6 weeks delivery', value:'Four Weeks', text:'Made To Order'},
{description:'(unavailable on this item)', value:'Rush', text:'Express Delivery', disabled:true}
];
$("#DropItDelivery").msDropDown({byJson:{data:deliveryData, name:'delivery', width: 200, selectedIndex: 1}}).data("dd");
paymentData = [
{ description:'How would you like to pay?', value:'Payment', text:'Payment Method'},
{image:'images/msdropdown/icons/Visa-56.png', description:'Secure online payment', value:'Visa', text:'Visa'},
{image:'images/msdropdown/icons/Paypal-56.png', description:'Secure online payment', value:'Paypal', text:'Paypal'},
{image:'images/msdropdown/icons/EmailPay-56.png', description:'Order by email', value:'Email Payment', text:'Send Your Details'},
{image:'images/msdropdown/icons/Mastercard-56.png', description:'(coming soon)', value:'Mastercard', text:'Mastercard', disabled:true},
{image:'images/msdropdown/icons/Collect-56.png', description:'(coming soon)', value:'Collection', text:'Order and Collect', disabled:true},
{image:'images/msdropdown/icons/Email-56.png', description:'email Menna', value:'Other Method', text:'Alternatives'}
];
$("#DropItPayments").msDropDown({byJson:{data:paymentData, name:'payments', width: 250}}).data("dd");
}
$(document).ready(function(e) {
//no use
try {
var pages = $("#pages").msDropdown({on:{change:function(data, ui) {
var val = data.value;
if(val!="")
window.location = val;
}}}).data("dd");
var pagename = document.location.pathname.toString();
pagename = pagename.split("/");
pages.setIndexByValue(pagename[pagename.length-1]);
$("#ver").html(msBeautify.version.msDropdown);
} catch(e) {
//console.log(e);
}
$("#ver").html(msBeautify.version.msDropdown);
//convert
$("select").msDropdown();
createByJson();
$("#tech").data("dd");
});
function showValue(h) {
console.log(h.name, h.value);
}
$("#tech").change(function() {
console.log("by jquery: ", this.value);
})
//
And the html:
<div id="dropOptions">
<div id="dropOptionsTitle"><p>Item</p></div>
<div id="DropItBlodeuwedd"></div>
</div>
<div id="dropOptions">
<div id="dropOptionsTitle"><p>Precious Stones</p></div>
<div id="DropItPearls"></div>
</div>
<div id="dropOptions">
<div id="dropOptionsTitle"><p>Payment</p></div>
<div id="DropItPayments"></div>
</div>
<div id="dropOptions">
<div id="dropOptionsTitle"><p>Delivery</p></div>
<div id="DropItDelivery"></div>
</div>
<div id="dropOptions">
<div id="dropOptionsTitle"><p>Buy Now!</p></div>
<div id="DropItBuy"></div>
</div>
Again, working version viewable here
Many thanks in advance!
What I think you want is for your Buy button to dynamically read what the dropdowns currently say and build a link for redirection based on that, rather than trying to update the Buy button every time a dropdown changes.
From your code I can't see what the form of the final URL is supposed to be. For example, to get the current value of the delivery option, you can check $('#DropItDelivery :selected').text() which will be something like "Made To Order".
Your Buy Now! could be a button with a click event that reads these values and constructs the URL with basic string concatenation, e.g.:
window.location = "buynow.html?delivery=" + $('#DropItDelivery :selected').text() +
"&payment=" + $('#DropItPayments :selected').text()
// etc.
Of course you'd have to handle these options on the server.
In case you want to redirect to the payment page of the processor, you can just branch based on the payment method and give them the URL you want based on that.
var pm = $('#DropItPayments :selected').text();
if (pm == "Visa")
{
// Visa payment URL construction
}
else if (pm == "Send Your Details")
{
// Send your details URL construction
}
// etc.

Categories

Resources