I am going to create a simple slider from available JSON object. I want to scroll 3 item i.e. 3 keys of JSON in single click either left or right.
Example: If I clicked right arrow then I want to fetch 0 to 2 keys of JSON and display image and if again right arrow then 3 to 6 and so on. Similarly in case of left arrow clicked. I want to make negative loop from current position of JSONkeys like 6 to 3.
I tried my code But its not working well.
var recents = "";
var imges = "";
var imge = "";
var recent_prod = <?php echo $recent_prod; ?>;
$("#num").html(recent_prod.length);
for(var a = 0; a < 3; a++)
{
imges = recent_prod[a].image;
imge = imges.split[","];
recents += '<a href="' + base_url + 'init/product/' + recent_prod[a].id + '">'+
'<div class="related_prod_thumb">' +
'<div class="related_prod_img">'+
'<span class="helper"></span>'+
'<img src="' + base_url + 'uploads/thumbnail/' + imges + '" width="100">'+
'</div><div class="related_prod_title">' + recent_prod[a].title +'</div>'+
'<div class="related_prod_price">' + 'Rs. ' + recent_prod[a].price + '</div></div></a>';
}
$("#recent_views").html(recents);
$(document).on("click", ".rightarr", function(){
var next_recent_prod = "";
var next = a + 3;
for(var i = a; i < next; i++)
{
imges = recent_prod[i].image;
imge = imges.split[","];
next_recent_prod += '<a href="' + base_url + 'init/product/' + recent_prod[i].id + '">'+
'<div class="related_prod_thumb">' +
'<div class="related_prod_img">'+
'<span class="helper"></span>'+
'<img src="' + base_url + 'uploads/thumbnail/' + imges + '" width="100">'+
'</div><div class="related_prod_title">' + recent_prod[i].title +'</div>'+
'<div class="related_prod_price">' + 'Rs. ' + recent_prod[i].price + '</div></div></a>';
a = a + 1;
}
$("#num").html(a);
$("#recent_views").html(next_recent_prod);
});
$(document).on("click", ".leftarr", function(){
var next_recent_prod = "";
var pre = a - 3;
for(var i = pre; i >= 0; i--)
{
imges = recent_prod[i].image;
imge = imges.split[","];
next_recent_prod += '<a href="' + base_url + 'init/product/' + recent_prod[i].id + '">'+
'<div class="related_prod_thumb">' +
'<div class="related_prod_img">'+
'<span class="helper"></span>'+
'<img src="' + base_url + 'uploads/thumbnail/' + imges + '" width="100">'+
'</div><div class="related_prod_title">' + recent_prod[i].title +'</div>'+
'<div class="related_prod_price">' + 'Rs. ' + recent_prod[i].price + '</div></div></a>';
}
$("#num").html(a);
$("#recent_views").html(next_recent_prod);
a = i;
});
With this code I get negative keys of JSON when clicked left. That is -1 but its doesn't exists in JSON. So I get error TypeError. Also Its not working as expected
Any help would be grateful. Thank you.
It seems your going from a to next which is a+3 for the right arrow, but for the left arrow you're going from 0 to pre which is supposed to be a-3. You probably mean:
for(var i = a-1; i >= pre; i--)
You have a = i after the loop in your left arrow click, when that loop ends the value of i will be -1 (or if corrected #1 it'll be one below the desired value), So you probably would want:
a = i + 1;
Or like you do for the right arrow, have it insides your loop:
a = a - 1; //or in short a--;
For left arrow you need to check whether it reaches zero and if so only show the first 3 items, disable the left arrow, etc:
var pre;
if(a > 2)
pre = a - 3;
else {
pre = 2;
//disable left & make sure you enable it when right is clicked.
}
Do the same for the right arrow, check whether it exceeds the length:
//not sure about 4, try 3 or 2 maybe if it doesn't work
if(a < recent_prod.length - 4)
next = a + 3;
else {
next = recent_prod.length - 3;
//disable right & make sure you enable it when left is clicked.
}
Related
Let's say I have some sentences in Google Docs. Just one sentences as an example:
"My house is on fire"
I actually changed the background color so that every verb is red and every noun blue.
Now I want to make a list with all the verbs and another one with the nouns. Unfortunately getBackgroundColor() only seems to work with paragraphs and not with single words.
My idea was, to do something like this (I didn't yet have the time to think about how to do the loop, but that's not the point here anyway):
var doc = DocumentApp.getActiveDocument();
var body = doc.getBody();
var paragraphs = body.getParagraphs();
var colorVar = paragraphs[0].getText().match(/\w+/).getBackgroundColor(); // The regEx matches the first word. Next I want to get the background color.
Logger.log(colorVar);
}
The error message I get goes something like this:
"The function getBackgroundColor in the text object couldn't be found"
Thx for any help, or hints or comments!
You want to retrieve the text from a paragraph.
You want to retrieve each word and the background color of each word from the retrieved the text.
In this case, the color is the background color which is not getForegroundColor().
You want to achieve this using Google Apps Script.
If my understanding is correct, how about this answer? Please think of this as just one of several possible answers.
At first, the reason of your error is that getBackgroundColor() is the method of Class Text. In your script, getBackgroundColor() is used for the string value. By this, the error occurs.
In this answer, for achieving your goal, each character of the text retrieved from the paragraph is scanned, and each word and the background color of each word can be retrieved.
Sample script:
function myFunction() {
var doc = DocumentApp.getActiveDocument();
var body = doc.getBody();
var paragraphs = body.getParagraphs();
var textObj = paragraphs[0].editAsText();
var text = textObj.getText();
var res = [];
var temp = "";
for (var i = 0; i < text.length; i++) {
var c = text[i];
if (c != " ") {
temp += c;
} else {
if (temp != "") res.push({text: temp, color: textObj.getBackgroundColor(i - 1)});
temp = "";
}
}
Logger.log(res) // result
}
When you run the script, the text of 1st paragraph is parsed. And you can see the result with res as an object.
In this sample script, the 1st paragraph is used as a test case. So if you want to retrieve the value from other paragraph, please modify the script.
References:
getBackgroundColor()
getBackgroundColor(offset)
editAsText()
If I misunderstood your question and this was not the direction you want, I apologize.
Here's a script your welcome to take a look at. It highlights text that a user selects...even individual letters. I did it several years ago just to learn more about how documents work.
function highLightCurrentSelection() {
var conclusionStyle = {};
conclusionStyle[DocumentApp.Attribute.BACKGROUND_COLOR]='#ffffff';
conclusionStyle[DocumentApp.Attribute.FOREGROUND_COLOR]='#000000';
conclusionStyle[DocumentApp.Attribute.FONT_FAMILY]='Calibri';
conclusionStyle[DocumentApp.Attribute.FONT_SIZE]=20;
conclusionStyle[DocumentApp.Attribute.BOLD]=false;
conclusionStyle[DocumentApp.Attribute.HORIZONTAL_ALIGNMENT]=DocumentApp.HorizontalAlignment.LEFT;
conclusionStyle[DocumentApp.Attribute.VERTICAL_ALIGNMENT]=DocumentApp.VerticalAlignment.BOTTOM;
conclusionStyle[DocumentApp.Attribute.LINE_SPACING]=1.5;
conclusionStyle[DocumentApp.Attribute.HEIGHT]=2;
conclusionStyle[DocumentApp.Attribute.LEFT_TO_RIGHT]=true;
var br = '<br />';
var selection = DocumentApp.getActiveDocument().getSelection();
var s='';
if(selection) {
s+=br + '<strong>Elements in Current Selection</strong>';
var selectedElements = selection.getRangeElements();
for(var i=0;i<selectedElements.length;i++) {
var selElem = selectedElements[i];
var el = selElem.getElement();
var isPartial = selElem.isPartial();
if(isPartial) {
var selStart = selElem.getStartOffset();
var selEnd = selElem.getEndOffsetInclusive();
s+=br + 'isPartial:true selStart=' + selStart + ' selEnd=' + selEnd ;
var bgcolor = (el.asText().getBackgroundColor(selStart)=='#ffff00')?'#ffffff':'#ffff00';
el.asText().setBackgroundColor(selStart, selEnd, bgcolor)
}else {
var selStart = selElem.getStartOffset();
var selEnd = selElem.getEndOffsetInclusive();
s+=br + 'isPartial:false selStart=' + selStart + ' selEnd=' + selEnd ;
var bgcolor = (el.asText().getBackgroundColor()=='#ffff00')?'#ffffff':'#ffff00';
el.asText().setBackgroundColor(bgcolor);
}
var elType=el.getType();
s+=br + 'selectedElement[' + i + '].getType()= ' + elType;
if(elType==DocumentApp.ElementType.TEXT) {
var txt = selElem.getElement().asText().getText().slice(selStart,selEnd+1);
var elattrs = el.getAttributes();
if(elattrs)
{
s+=br + 'Type:<strong>TEXT</strong>';
s+=br + 'Text:<span style="color:#ff0000">' + txt + '</span>';
s+=br + 'Length: ' + txt.length;
s+=br + '<div id="sel' + Number(i) + '" style="display:none;">';
for(var key in elattrs)
{
s+= br + '<strong>' + key + '</strong>' + ' = ' + elattrs[key];
s+=br + '<input type="text" value="' + elattrs[key] + '" id="elattr' + key + Number(i) + '" />';
s+=br + '<input id="elattrbtn' + Number(i) + '" type="button" value="Save Changes" onClick="setSelectedElementAttribute(\'' + key + '\',' + i + ');" />'
}
s+='</div>Show/Hide';
}
}
if(elType==DocumentApp.ElementType.PARAGRAPH) {
var txt = selElem.getElement().asParagraph().getText();
var elattrs = el.getAttributes();
if(elattrs)
{
s+=br + '<strong>PARAGRAPH Attributes</strong>';
s+=br + 'Text:<span style="color:#ff0000">' + txt + '</span> Text Length= ' + txt.length;
for(var key in elattrs)
{
s+= br + key + ' = ' + elattrs[key];
}
}
}
s+='<hr width="100%"/>';
}
//var finalP=DocumentApp.getActiveDocument().getBody().appendParagraph('Total Number of Elements: ' + Number(selectedElements.length));
//finalP.setAttributes(conclusionStyle);
}else {
s+= br + 'No Elements found in current selection';
}
s+='<input type="button" value="Toggle HighLight" onclick="google.script.run.highLightCurrentSelection();"/>';
//s+='<input type="button" value="Exit" onClick="google.script.host.close();" />';
DocumentApp.getUi().showSidebar(HtmlService.createHtmlOutputFromFile('htmlToBody').append(s).setWidth(800).setHeight(450).setTitle('Selected Elements'));
}
I wrote this code and it works:
function getJsonResult(retrieve) {
var result = retrieve.results;
for (var i = 0; i < result.length; i++) {
responseJson.push({ id: result[i].id, title: result[i].title });
var search = '<a id="' + result[i].id + '">' + result[i].title + '</a><br/>';
document.write(search);
}
}
When I tried to display the results in a div, I change the last line with:
$("#divId").html(search);
But it only displays the first result. How can I make the whole list appear?
That happened because you're overriding the search variable in every iteration :
var search = '<a id="' + result[i].id + '">' + result[i].title + '</a><br/>';
You need to declare the search variable outside of the loop then append the string in every iteration like :
function getJsonResult(retrieve) {
var result = retrieve.results;
var search = "";
___________^^^^
for (var i = 0; i < result.length; i++) {
responseJson.push({ id: result[i].id, title: result[i].title });
var search += '<a id="' + result[i].id + '">' + result[i].title + '</a><br/>';
___________^^
document.write(search);
}
}
Then finally you could put your variable content to the div :
$("#divId").html(search);
$('#divId').append(search);
This appends the element included in search to the div element.
Currently able to filter through "teams" and say if it matches x then display everything associated with it. The problem is method searching through hard codes the team category names, but need it to be able to say instead programmatically, for each unique team type sort by that.
As you can see below my solution requires triple statements when it could be covered in just one single object oriented method.
$('#jobs-container .jobs-list').append(
'<div id="teamtop"><span>Legal</span></div>');
for (i = 0; i < _data.length; i++) {
for (j = 0; j < _data[i].postings.length; j++) {
var posting = _data[i].postings[j]
var title = posting.text
var description = posting.description
//Making each job description shorter than 250 characters
var shortDescription = $.trim(description).substring(0, 250)
.replace('\n', ' ') + "...";
var location = nullCheck(posting.categories.location);
var locationCleanString = cleanString(location);
var commitment = nullCheck(posting.categories.commitment);
var commitmentCleanString = cleanString(commitment);
var team = nullCheck(posting.categories.team);
var teamCleanString = cleanString(team);
var link = posting.hostedUrl + leverParameter;
if (team == "Legal") {
$('#jobs-container .jobs-list').append(
'<div class="job ' + teamCleanString + ' ' + locationCleanString + ' ' + commitmentCleanString + '">' +
'<a class="job-title" href="' + link + '"">' + title + '</a>' +
'</div>'
);
}
}
}
$('#jobs-container .jobs-list').append(
'<div id="teamtop"><span>Engineering</span></div>');
for (i = 0; i < _data.length; i++) {
for (j = 0; j < _data[i].postings.length; j++) {
var posting = _data[i].postings[j]
var title = posting.text
var description = posting.description
//Making each job description shorter than 250 characters
var shortDescription = $.trim(description).substring(0, 250)
.replace('\n', ' ') + "...";
var location = nullCheck(posting.categories.location);
var locationCleanString = cleanString(location);
var commitment = nullCheck(posting.categories.commitment);
var commitmentCleanString = cleanString(commitment);
var team = nullCheck(posting.categories.team);
var teamCleanString = cleanString(team);
var link = posting.hostedUrl + leverParameter;
if (team == "Engineering") {
$('#jobs-container .jobs-list').append(
'<div class="job ' + teamCleanString + ' ' + locationCleanString + ' ' + commitmentCleanString + '">' +
'<a class="job-title" href="' + link + '"">' + title + '</a>' +
'</div>'
);
}
}
}
$('#jobs-container .jobs-list').append(
'<div id="teamtop"><span>Operations</span></div>');
for (i = 0; i < _data.length; i++) {
for (j = 0; j < _data[i].postings.length; j++) {
var posting = _data[i].postings[j]
var title = posting.text
var description = posting.description
//Making each job description shorter than 250 characters
var shortDescription = $.trim(description).substring(0, 250)
.replace('\n', ' ') + "...";
var location = nullCheck(posting.categories.location);
var locationCleanString = cleanString(location);
var commitment = nullCheck(posting.categories.commitment);
var commitmentCleanString = cleanString(commitment);
var team = nullCheck(posting.categories.team);
var teamCleanString = cleanString(team);
var link = posting.hostedUrl + leverParameter;
if (team == "Operations") {
$('#jobs-container .jobs-list').append(
'<div class="job ' + teamCleanString + ' ' + locationCleanString + ' ' + commitmentCleanString + '">' +
'<a class="job-title" href="' + link + '"">' + title + '</a>' +
'</div>'
);
}
}
}
I have tried to do a for each around the team but am struggling to output properly:
for(i = 0; i < team.length; i++) {
alert ("output only teams once"+team);
}
I have attached more or less the visual concept that is trying to be achieved although the CSS styling is not necessary right now, more so focused on grouping the titles by teams.
So we are getting the correct out put such as
Legal
Corporate Associate
Corporate Paralegal
Junior Corporate Associate, Blockchain
Junior Corporate Associate, Emerging Growth
Legal Document Specialist
Regulatory & Compliance Counsel
But we are manually matching to legal, just want to filter through each team and see instead.
Vngeener answer repeats team each time, need it to only print out the team one time.
You do not really need to create "Teamtop" divs manually.
The for loop you have created should handle that.
And you do not need the duplicated for loop code for each team heading.
And in the loop "team" condition is not needed.
The way code is written, that's not utilizing the for-loop capability properly.
Try replacing your code with the code given below (Only once, do not repeat this code for multiple conditions):
var teamAdded = [];
for(i = 0; i < _data.length; i++) {
for (j = 0; j < _data[i].postings.length; j ++) {
var posting = _data[i].postings[j]
var title = posting.text
var description = posting.description
//Making each job description shorter than 250 characters
var shortDescription = $.trim(description).substring(0, 250)
.replace('\n', ' ') + "...";
var location = nullCheck(posting.categories.location);
var locationCleanString = cleanString(location);
var commitment = nullCheck(posting.categories.commitment);
var commitmentCleanString = cleanString(commitment);
var team = nullCheck(posting.categories.team);
var teamCleanString = cleanString(team);
var link = posting.hostedUrl+leverParameter;
//Add Team top heading dynamically
if (!teamAdded[team]){
$('#jobs-container .jobs-list').append(
'<div id="teamtop"><span>'+ team +'</span></div><div id="team-children" data-team="'+ team +'"></div>');
teamAdded[team] = true;
}
// team condition was not required here
// if(team=="Legal"){
$('[data-team="'+ team +'"]').append(
'<div class="job '+teamCleanString+' '+locationCleanString+' '+commitmentCleanString+'">' +
'<a class="job-title" href="'+link+'"">'+title+'</a>' +
'</div>'
);
}
}
trying to prepend my list in jquery mobile but I just can't get the divider to be on top of the most recent item added to the listview.
I've tried prepending the item that's being added but it then switches the divider to the bottom.
function loadScanItems(tx, rs) {
var rowOutput = "";
var $scanItems = $('#scanItems');
$scanItems.empty();
var bubbleCount = 0;
for (var i = 0; i < rs.rows.length; i++) {
bubbleCount = bubbleCount + 1;
//rowOutput += renderScan(rs.rows.item(i));
var row = rs.rows.item(i)
var now = row.added_on;
var date = get_date(now);
rowOutput += '<li data-icon="false"><div class="ui-grid-b"><div class="ui-block-a" style="width:50%"><h3>Su # ' + row.sunum + '</h3><p> Bin # ' + row.binnum + '</p></div><p class="ui-li-aside"><strong>' + date + '</strong></p><div class="ui-block-b" style="width:20%"></div><div class="ui-block-c" style="width:25%"><br><p>User: ' + row.userid + '</p></div></div></li>';
// rowOutput += '<li>' + row.sunum + row.binnum+ "<a href='javascript:void(0);' onclick='webdb.deleteScan(" + row.ID + ");'>Delete</a></li>";
}
$scanItems.append('<li data-role="list-divider">Scanned Items <span class="ui-li-count">' + bubbleCount + '</span></li>').listview('refresh');
$scanItems.append(rowOutput).listview('refresh');
}
The code is above with it correctly formatted with the divider on top but the list items being appended to the bottom instead of prepended to the top.
Thanks!
The problem is that your are building a string with all the scan items. That string already has an order so whether you prepend or append makes no difference. Try this simple change.
Change:
rowOutput += '<li data-icon="false">...</li>';
to:
rowOutput = '<li data-icon="false">...</li>' + rowOutput;
This will put your rowOutput string in the correct order before appending to the listview.
Here is a working DEMO
Basically, I'm using JavaScript to dynamically generate a form that allows from multiple entries within a single submission. Here's the code I'm using for that:
function addEvent()
{
var ni = document.getElementById('myDiv');
var numi = document.getElementById('theValue');
var num = (document.getElementById('theValue').value - 1) + 2;
numi.value = num;
var divIdName = 'my' + num + 'Div';
var newdiv = document.createElement('div');
newdiv.setAttribute('id', divIdName);
newdiv.innerHTML = '<table id="style" style="background-color: #ffffff;"><tr><td colspan="2">Entry ' + num + '<hr \/><\/td><\/tr><tr><td><label>Item 1: <\/td><td><input name="item1_' + num + '" value="" type="text" id="item1" \/><\/label><\/td><\/tr><tr><td><label>Item 2: <\/td><td><input name="item2_' + num + '" type="text" id="item2" \/><\/label><\/td><\/tr><tr><td><label>Item 3: <\/td><td><input type="text" name="item3_' + num + '" id="item3" \/><\/label><\/td><\/tr><tr><td><label>Item 4: <\/td><td><select name="item4_' + num + '" id="item4"><option value="---">---<\/option><option value="opt_1">1<\/option><option value="opt_2">2<\/option><option value="opt_3">3<\/option><option value="opt_4">4<\/option><\/select><\/label><\/td><\/tr><\/table>';
ni.appendChild(newdiv);
}
This works just fine, generating the entries fields I need. Using console in-browser, I've even verified all the names are correct. The issue is that I need to then take the selections and generate output. I've tried several methods, but everything resulted in null values.
function generateVideo()
{
var entries = document.getElementById('theValue').value;
var item1 = {};
var item2 = {};
var item3 = {};
var item4 = {};
for(i = 1; i <= entries; i++)
{
item1[i - 1] = document.getElementById('item1_' + i);
item2[i - 1] = document.getElementById('item2_' + i);
item3[i - 1] = document.getElementById('item3_' + i);
item4[i - 1] = document.getElementById('item4_' + i);
}
var code = 'Copy code and paste it into Notepad<br \/>"Save as" filename.html<br \/><textarea name="" cols="45" rows="34">header template\n';
for(i = 0; i < entries; i++)
{
if(i != (entries - 1))
{
code = code + ' ["' + item1[i] + '", "' + item2[i] + '", "' + item3[i] + '", "' + item4[i] + '"],\n';
}
else
{
code = code + ' ["' + item1[i] + '", "' + item2[i] + '", "' + item3[i] + '", "' + item4[i] + '"]\n';
}
}
code = code + 'footer template<\/textarea>';
var result = document.getElementById("result");
result.innerHTML = code;
}
The output is as follows:
Copy code and paste it into Notepad<br />"Save as" CourseName_Unit_Chapter.html<br /><textarea name="" cols="45" rows="34">header template
["null", "null", "null", "null"]
footer template</textarea>
Now, certain fields can be null, that's fine (I'll do form validation after I get it working), but I'm getting null for every field regardless of what is entered.
I, originally, had the .value on the getElementByIds, but that only results in the script not running when the entries variable is greater than 0 (default), which is why I tried removing them.
function generateVideo()
{
var entries = document.getElementById('theValue').value;
var item1 = {};
var item2 = {};
var item3 = {};
var item4 = {};
for(i = 1; i <= entries; i++)
{
item1[i - 1] = document.getElementById('item1_' + i).value;
item2[i - 1] = document.getElementById('item2_' + i).value;
item3[i - 1] = document.getElementById('item3_' + i).value;
item4[i - 1] = document.getElementById('item4_' + i).value;
}
var code = 'Copy code and paste it into Notepad<br \/>"Save as" filename.html<br \/><textarea name="" cols="45" rows="34">header template\n';
for(i = 0; i < entries; i++)
{
if(i != (entries - 1))
{
code = code + ' ["' + item1[i] + '", "' + item2[i] + '", "' + item3[i] + '", "' + item4[i] + '"],\n';
}
else
{
code = code + ' ["' + item1[i] + '", "' + item2[i] + '", "' + item3[i] + '", "' + item4[i] + '"]\n';
}
}
code = code + 'footer template<\/textarea>';
var result = document.getElementById("result");
result.innerHTML = code;
}
I've also tried variations of multidimensional arrays, instead of four arrays, but got the same results.
The output, as indicated by the removal of the .value on the getElementByIds, is good. Basically, there is something wrong with my attempts to populate the arrays using the dynamically generated forms.
I suspect that the issue with the declaration of the element ID, but I'm not sure how else to declare it. This style of scripting is not my norm. ^^'
Anyone have any ideas on how to fix the for loop to generate the array?
replace all occurences of
itemN[i]
with
itemN[i].value
if that doesnt work add
console.log( itemN[i] )
and see what it outputs