I'm making my own dropdown script in jQuery. Things are going well, but I'm running into a problem. Whenever I enter any characters into the text field, all elements in the array I am searching are displayed, instead of the elements that match what's in the textbox.
For example, if I regex search for "ra" against my array of:
var planes = [
'Alara',
'Fiora',
'Innistrad',
'Kamigawa',
'Lorwyn',
'Mirrodin',
'Ravnica',
'Shandalar',
'Zendikar'
];
I should only see Alara, Fiora, Innistrad and Ravnica in the autocomplete.
Here's a Plunker.
Any help is greatly appreciated.
You need to compare to -1, so it will only show if it is found. You are currently comparing to 1 instead, so it returns true for all items. Probably a typo. Good luck!
else{
//Grep used to search array but not alter the original.
var results = $.grep(planes, function(item){
return item.search(new RegExp(query, "i")) != *add a - here* 1;
});
console.log("Added " + query + " to cache.");
cache[query] = results;
}
Related
I have a scenario like Need to edit the single quotes values (only single quotes values),
So I extracted the single quotes values using regex and prepare the reactive dynamic form.
onclick of performing edit button will show old step name above, new step name below, submit step will replace the step name in the original array.
WOrking fine as expected in few scenarios according to my approach, but in scenarios, I realized whatever algorithm I am following does not fulfill my requirement.
Below are the test cases
Test case 1:
Step Name: "Then I should hire an employee using profile '1' for 'USA'",
// Here --> '1', 'USA' values are editable
Test case 2: "And Employee should be hired on '01' day of pay period '01' of 'Current' Fiscal"
// '01', '01', 'Current'
Issues: in test case 2 if I tried to edit second 01 it is editing the first 01
I try to solve the perform edit function with help of indexof, substring functions
this.replaceString = this.selectedStep.name;
this.metaArray.forEach((element: any) => {
var metaIndex = this.replaceString.indexOf(element.paramValue);
if (metaIndex !== -1) {
const replaceValue = this.stepEditForm.controls[element['paramIndex']].value;
this.replaceString = this.replaceString.substring(0, metaIndex) + replaceValue + this.replaceString.substring(metaIndex + (element.paramValue.length));
}
});
but in indexof always find the first occurrence of a value in a string. So I realized my approach is wrong on performed it function
please find the attachment for the code
https://stackblitz.com/edit/angular-reactive-forms-cqb9hy?file=app%2Fapp.component.ts
So Can anyone please suggest to me how to solve this issue,
Thanks in advance
I added a function called matchStartingPositions that returns the starting position indexes of each match. Using this method you can then perform your edit by replacing the string just as you do, but we'll find the proper match to be replaced at the given position.
So in your line
var metaIndex = this.replaceString.indexOf(element.paramValue);
we can then add a second parameter to indexOf, that is the starting point:
var metaIndex = this.replaceString.indexOf(element.paramValue, startingPositions[element.paramIndex]);
The function for getting the index positions just looks for those single quotes in a given string:
matchStartingPositions(str) {
let count = 0;
let indices = [];
[...str].forEach((val, i) => {
if (val === "'") {
if (count % 2 == 0) {
indices.push(i);
}
count++;
}
});
return indices;
}
Here it is in action:
https://angular-reactive-forms-xhkhmx.stackblitz.io
https://stackblitz.com/edit/angular-reactive-forms-xhkhmx?file=app/app.component.ts
I have an array of email addresses that I obtained using .getViewers() from my sheet. This gives me the array of
[xxxxxjrhigh#xxxxxxx.org, /hd/domain/xxxxxxx.org, testemail3#googlemail.com, testemail2#gmail.com, testemail1#gmail.com]
Note: xxxxxxx replacing sensitive information
I am trying to remove the following from that array and then send an email to the remaining email addresses.
xxxxxjrhigh#xxxxxxx.org -and- /hd/domain/xxxxxxx.org
The index results always come back as -1 (no match found).
I'm new to coding so I'm sure it is an easy fix that I am just not aware of. I have tried putting my search term in 'single' quotes, in "double" quotes, and in no quotes at all. I tried assigning it to a variable and then using the variable in the indexOf(variable). I've watch 3 different tutorials on using indexOf() that do not indicate that I should have any trouble.
var viewers = SpreadsheetApp.getActiveSpreadsheet().getViewers();
Logger.log(viewers);
var index = viewers.indexOf('/hd/domain/xxxxxxx.org');
Logger.log(index);
viewers.splice( index, 1);
Logger.log(viewers);
var index = viewers.indexOf('xxxxxjrhigh#xxxxxxx.org');
Logger.log(index);
viewers.splice( index, 1);
Logger.log(viewers);
var string = ""+viewers;
Logger.log(string);
GmailApp.sendEmail(string, 'Test Treacker', 'This is the outcome from the test tracker');
Results I have been getting from the log:
index = -1.0
index = -1.0
string = xxxxxjrhigh#xxxxxxx.org,/hd/domain/xxxxxxx.org,testemail3#googlemail.com,testemail2#gmail.com
What I expect to get:
index = 0
index = 1
string = testemail3#googlemail.com,testemail2#gmail.com
You can take a look at what getViewers() call returns here: https://developers.google.com/apps-script/reference/spreadsheet/spreadsheet.html#getviewers. It is not an array of strings, but rather an array of User objects, each of which has a getEmail() method. The reason why your indexOf() returns a -1 for every email is that you are not working with an array of simple strings here!
To remove two users from the array based on their email you could do something like this:
const viewers = SpreadsheetApp.getActiveSpreadsheet().getViewers();
const filteredViewers = viewers.filter(viewer =>
viewer.getEmail() !== 'email1' && viewer.getEmail() !== 'email2');
Where email1 and email2 are emails of users you don't want to have in your resulting array.
Thank you #ajobi for pointing me in the right direction. While your code didn't help me because of the odd syntax error, your revelation that the items in my viewers array where accounts instead of actual email addresses got me thinking and doing a little more research. I stumbled on an answer that works for me.
I mapped the array of accounts to change it to an array of actual email addresses. This is what I came up with.
function correctEmails() {
var viewers = SpreadsheetApp.getActiveSpreadsheet().getViewers();
Logger.log(viewers);
var viewers1 = viewers.map(getEmails);
Logger.log(viewers1);
var index = viewers1.indexOf('/hd/domain/xxxxxxx.org');
Logger.log(index);
viewers1.splice( index, 1);
Logger.log(viewers1);
var index = viewers1.indexOf('xxxxxjrhigh#xxxxxxx.org');
Logger.log(index);
viewers1.splice( index, 1);
Logger.log(viewers1);
var string = ""+viewers1;
Logger.log(string+" - string");
// GmailApp.sendEmail(string, 'Test Treacker', 'This is the outcome from the test tracker');
//
}
function getEmails(item) {
return item.getEmail();
}
This results in the string I was looking for of testemail3#googlemail.com,testemail2#gmail.com and it will work no matter what order the email accounts are in.
Thanks!
I'm creating a filter using select elements. This is for a wheel store, so the values would be bolt patterns, sizes, colors, etc.
I have to make an AJAX call with all the selected values in the format:
value1+value2+value3....
The only way I could think of to do this would be to iterate over the selected options and add to the sign + and the selected value to the string and in the end use substring to remove the first + sign.
var SelectedFilters = '';
$('#CategoryFilter .BlockContent select').each(function(index, element) {
value = $(element).find('option:selected').val();
if(value != "Choose One"){
SelectedFilters += ('+' + value); // This is the line with the problem
});
SelectedFilters = SelectedFilters.substring(1,SelectedFilters.length);
The problem I'm having is with line 5 above. I'm getting a Syntax, unexpected token error, but I cannot figure out what is wrong with my syntax.
There's nothing wrong with that line, but there's something wrong with the next line:
});
If that's supposed to be the end of the .each() callback, then you're missing the } for the if statement. If it's not supposed to be the end of the function, then the ); is wrong.
You have some syntax errors, use JSLint or JSHint to fix them.
Also, you can greatly simplify this process:
var SelectedFilters = $('#CategoryFilter .BlockContent option:selected')
.filter(function () { return this.value !== 'Choose One'; })
.map(function () { return this.value; }).get().join('+');
entirely in JS, no server backend. I need to allow the user to search and then show a list of matched names. I'm using jQuery UI AutoComplete but need some JS to filter the results.
Given an Array of names:
Bob Hope
James Jones
Steve Jobs
Larry McBridge
Given a search term like Bo
How can I get just Bob Hope to return
Given a Search term like b:
How can I get all but James Jones?
Any simple JS for comparing two strings? Thanks
var names = ["Bob Hope","James Jones","Steve Jobs","Larry McBridge"]
var query = "bo"
var results = $(names)
.map(function(i,v){
if(v.toLowerCase().indexOf(query.toLowerCase())!=-1){return v}
}).get()
// results is ["Bob Hope"]
Maybe I misunderstood you (given the complexity of the above answer), but I came up with this which uses jQuery. Every time a key is pressed (when the input has focus), it searches all li elements on the page and finds whether they contain the search term.
Here is the HTML:
<ul><li>Bob Hope</li>
<li>James Jones</li>
<li>Steve Jobs</li>
<li>Larry McBridge</li></ul><br>
Search: <input id="search" length="24" />
And here is your jQuery:
$("#search").keyup(function(){
$("li").hide();
var term = $(this).val();
$("li:contains('" + term + "')").show();
});
Using Ivan's answer, but with ES6 changes:
var names = ["Bob Hope","James Jones","Steve Jobs","Larry McBridge"];
function findIn(s, list){
return list.filter((v) => v.toLowerCase().indexOf(s.toLowerCase()) != -1 );
}
findIn('bo', names);
I want to take strings like:
Submit Changes
Create New
Update Record
Save Item
and convert them to:
Submitting Changes
Creating New
Updating Record
Saving Item
with a function like:
var ConvertToProgressivePresent = (function(){
// cache this regex
var rProgressivePresent = /\b(?:(Submi(t))|(Creat|Sav|Updat)e)\b/i;
return function(phrase){
return phrase.replace(rProgressivePresent, "$1$2$3ing");
};
}());
This above regex works but doesn't seem like the best way to do it. I don't like the grouping here where 1-2 groups are always empty when there is a match.
Got any suggestions or improvements?
If you have specific words to replace with then you could make a word bank. Have the words and their replacement stored in an object and then loop through it.
var ConvertToProgressivePresent = (function() {
var replaceValues = {
"Submit": "Submitting",
"Create": "Creating",
"Update": "Updating",
"Save": "Saving"
}
return function(phrase) {
for (var item in replaceValues) {
phrase = phrase.replace(item, replaceValues[item]);
}
return phrase;
};
}());
Here is a JSFiddle Example
I think you should probablly use CASE statments instead. Regex isn't the most efficient way of doing things...and that is probably best that it doesn't cuz you know the old saying.
Wow, I have this problem...I know, I'll use regex...ok, now you have two problems 90)
First off, it doesn't appear to me that your regex does quite what you want anyway in that I don't see a second "t" added when changing submit to submitting.
However, I don't think I would use regex for this task at all anyway. If you are just trying to replace one word with another, and the word always comes at the beginning of the string, I might do something like:
function ReplaceIfBeginsWith(wholeString, checkFor, replaceWith)
{
if (wholeString.indexOf(checkFor + ' ') == 0)
{
return replaceWith + ' ' + wholeString.substr(checkFor.length + 1);
}
if (wholeString == checkFor)
{
return replaceWith;
}
return wholeString;
}
Then, you can call the function with each of the words you would want to replace. If you want case-insensitivity, just check against lowercase versions of all the strings.