How to show next/previous links in Google Custom Search Engine paging links - google-custom-search

The Google Custom Search integration only includes numbered page links and I cannot find a way to include Next/Previous links like on a normal Google search. CSE used to include these links with their previous iframe integration method.

I stepped through the javascript and found the undocumented properties I was looking for.
<div id="cse" style="width: 100%;">Loading</div>
<script src="http://www.google.com/jsapi" type="text/javascript"></script>
<script type="text/javascript">
google.load('search', '1', {language : 'en'});
google.setOnLoadCallback(function() {
var customSearchControl = new google.search.CustomSearchControl('GOOGLEIDGOESHERE');
customSearchControl.setResultSetSize(google.search.Search.FILTERED_CSE_RESULTSET);
customSearchControl.setSearchCompleteCallback(null,
function() { searchCompleteCallback(customSearchControl) });
customSearchControl.draw('cse');
}, true);
function searchCompleteCallback(customSearchControl) {
var currentPageIndex = customSearchControl.e[0].g.cursor.currentPageIndex;
if (currentPageIndex < customSearchControl.e[0].g.cursor.pages.length - 1) {
$('#cse .gsc-cursor').append('<div class="gsc-cursor-page">Next</div>').click(function() {
customSearchControl.e[0].g.gotoPage(currentPageIndex + 1);
});
}
if (currentPageIndex > 0) {
$($('#cse .gsc-cursor').prepend('<div class="gsc-cursor-page">Previous</div>').children()[0]).click(function() {
customSearchControl.e[0].g.gotoPage(currentPageIndex - 1);
});
}
window.scrollTo(0, 0);
}
</script>
<link rel="stylesheet" href="http://www.google.com/cse/style/look/default.css" type="text/css" />

I've been using this to find the current page:
ctrl.setSearchCompleteCallback(null, function(gControl, gResults)
{
currentpage = 1+gResults.cursor.currentPageIndex;
// or, here is an alternate way
currentpage = $('.gsc-cursor-current-page').text();
});

And now it's customSearchControl.k[0].g.cursor ... (as of this weekend, it seems)
Next time it stops working just go to script debugging in IE, add customSearchControl as a watch, open the properties (+), under the Type column look for Object, (Array) and make sure there is a (+) there as well (i.e. contains elements), open[0], and look for Type Object, again with child elements. Open that and once you see "cursor" in the list, you've got it.

Related

Bootstrap input field inside tooltip popover removed from output html

Hello i`m using boostrap 4.3.1 and included popper 1.14.7.
Normally I can add input fields in the content of the popup/tooltip. I don`t since when, but at the moment when I put input field in the content then only the text is visible.
When I look in the source (compiled html) I can see that popper or bootstrap removed the input fields. Do I something wrong?
var options = {
html: true,
// content: function(){ return $(".amountElec.popup").html();},
placement: "bottom",
container: "body"
};
$(function(){
$('#manualinput').popover(options);
})
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" integrity="sha384-ggOyR0iXCbMQv3Xipma34MD+dH/1fQ784/j6cY/iJTQUOhcWr7x9JvoRxT2MZw1T" crossorigin="anonymous">
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.7/umd/popper.min.js"></script>
<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/js/bootstrap.min.js"></script>
<div id="manualinput"
data-container="body"
data-toggle="popover"
data-content="test <input name='test' type='text' value='2'>"
data-html="true"
data-placement="bottom">
OPEN TOOLTUP
</div>
It's even easier as you think:
Add
sanitize: false
as config option if you want to disable sanitize at all. If you just want to adapt the whitelist, you are right with your solution
https://github.com/twbs/bootstrap/blob/438e01b61c935409adca29cde3dbb66dd119eefd/js/src/tooltip.js#L472
I found the solution...
I my case add this to the javascript:
var myDefaultWhiteList = $.fn.tooltip.Constructor.Default.whiteList;
myDefaultWhiteList.input = [];
https://getbootstrap.com/docs/4.3/getting-started/javascript/#sanitizer
After searching in the debug console I found somehting in the tooltip.js from bootstrap.
content = sanitizeHtml(content, this.config.whiteList, this.config.sanitizeFn)
setElementContent($element, content) {
if (typeof content === 'object' && (content.nodeType || content.jquery)) {
// Content is a DOM node or a jQuery
if (this.config.html) {
if (!$(content).parent().is($element)) {
$element.empty().append(content)
}
} else {
$element.text($(content).text())
}
return
}
if (this.config.html) {
if (this.config.sanitize) {
content = sanitizeHtml(content, this.config.whiteList, this.config.sanitizeFn)
}
$element.html(content)
} else {
$element.text(content)
}
}
sanitizeHtml function removes the input fields :(.
I just turned of sanitize by default (globally):
$.fn.tooltip.Constructor.DEFAULTS.sanitize = false;
$.fn.popover.Constructor.DEFAULTS.sanitize = false;
https://getbootstrap.com/docs/3.4/javascript/#default-settings

Format/Layout for cshtml page

I got a lot of help regarding this issue earlier but the issue hasnt been completely resolved for me. I am stuck at another thing now. I am returning a response from my controller and receiving it in the Index.cshtml like this:
var rData = #Html.Raw(Json.Encode(Model.WarehouseResults));
Now I need to assign this data to slickgrid somewhat like this:
<script type="text/javascript">
var from = 0, to = from + rData.length;
//data.length = parseInt(resp.total);
for (var i = 0; i < rData.length; i++) {
data[from + i] = rData[i];
data[from + i].index = from + i;
}
onDataLoaded.notify({ from: from, to: to });
grid = new Slick.Grid("#myGrid", rData, columns, options);
etc etc...
</script>
Now, the problem is, I dont know where exactly to receive the data. As in, where do I put this line:
var rData = #Html.Raw(Json.Encode(Model.WarehouseResults));
If I put it above the tag (but inside the #Scripts section), I get an error saying rData is not defined. Then when I put it inside the tag, I get a syntax error saying: "IHtmlString HtmlHelper.Raw(String value) (+1 overloads) returns markup that is not HTML encoded".
Where exactly should this line go? Is there a standard format for a cshtml page, like which sections go where? If so, can someone provide a link or something for it?
Using your code in MVC 5:-
var rData = #Html.Raw(Json.Encode(Model.WarehouseResults));
I find that the semi-colon at the end of the line causes a syntax error.
A solution which I am currently using (my example is for JQuery autocomplete) which should also work for your example is as follows.
Create the javascript variable code completely within the HtmlHelper. This is placed within the view's #section Scripts.
#section Scripts {
<script type="text/javascript">
#Html.Raw("var existingPersons = " + Json.Encode(this.Model.ExistingPersons) + ";" )
#Html.Raw("var settlementInformation=" + Json.Encode(this.Model.SettlementInformation) + ";")
$(function () {
$("#personName").autocomplete({
source: existingPersons
});
$("#settlementInformation").autocomplete({
source: settlementInformation
});
});
</script>
}
At the client side this appears in the <head> element as expected
<script type="text/javascript">
var existingPersons = ["Person 1","Person 2"];
var settlementInformation=["Settlement Type 1"];
$(function () {
$("#personName").autocomplete({
source: existingPersons
});
$("#settlementInformation").autocomplete({
source: settlementInformation
});
});
</script>
I've not tried this in other versions of MVC

Using SPServices to disable a field if a user IS NOT a member of a specified SharePoint group

Working in SharePoint 2010 Foundation, I'm trying to disable a field on a custom editform.aspx for users who are not members of a specific group.
So, if current user is not a member of the group "Change Control - Admins", disable the CCID field.
I found what seemed to be the solution in the SPServices codeplex discussion area, but it doesn't work as expected. Not sure what I'm missing here.
It does disable the correct field, but does not matter if current user is in the specified group or not.
If i change this:
if($(xData.responseXML).find("Group[Name='Change Control - Admins']").length != 1)
to this:
if($(xData.responseXML).find("Group[Name='Change Control - Admins']").length == 1)
...then the field does not get disabled. However, it again doesn't matter if the current user is in the specified group or not.
Any help would be much appreciated.
Here's my code:
<script language="javascript" type="text/javascript" src="/CodeLibrary/jquery-1.7.2.min.js"></script>
<script language="javascript" type="text/javascript" src="/CodeLibrary/jquery.SPServices-0.7.2.min.ssl.js"></script>
<script language="javascript" type="text/javascript">
$(document).ready(function() {
var groupName;
$().SPServices({
operation: "GetGroupCollectionFromUser",
userLoginName: $().SPServices.SPGetCurrentUser(),
async: false,
completefunc: function(xData, Status) {
//if current user is not a member of this group...
if($(xData.responseXML).find("Group[Name='Change Control - Admins']").length != 1)
{
//...disable the following fields
$("input[Title='CCID']").prop("disabled", "disabled");
}
}
});
});
function PreSaveAction() {
$("input[Title='CCID']").removeProp("disabled");
return true;
}
</script>
I'm doing something very similar. In my case I'm checking the group membership for groups beginning with "GCP" and extracting some text from the matching groups. What has been really useful is logging to the Firefox console using console.log(). The Firefox console allows you to drill down into objects that you log to the console - something not provided by IE (this logging code should not be included in release code, particularly because it can fail in IE). The console is available from the Web Developer menu in Firefox.
$(document).ready(function() {
$().SPServices({
operation: "GetGroupCollectionFromUser",
userLoginName: $().SPServices.SPGetCurrentUser(),
async: false,
completefunc: function(xData, Status) {
console.log(xData.responseXML);
var $groups = $(xData.responseXML).find("Group[Name^='GCP']");
console.log("$groups.length:" + $groups.length);
if ($groups.length) console.log($groups.get(0).outerHTML);
var re = /GCP ((?:[^ ]*)(?:(?! Managers) [^ *]*)*) Managers/i;
var org = "";
$groups.each(function(index, elt){
var name = $(this).attr("Name");
var matches = re.exec(name);
if (matches){
org = matches[1];
return false;
}
});
setOrg(org);
}
});
});

Leaflet - updating a keyword search call to a restful api and refreshing map

My Question (UPDATED): How do I get my keyword to change in the API URL Search Query based off of an AJAX Call (having a scope problem here) ?
I connected a leaflet map to an an API to plot Wikipedia articles with geocoordinates. An example URL looks like: http://api.infochimps.com/encyclopedic/wikipedia/dbpedia/wikipedia_articles/search?g.radius=10000&g.latitude=30.3&g.longitude=-97.75&f.q=park&apikey=api_test-W1cipwpcdu9Cbd9pmm8D4Cjc469
So far so good. But I am stuck on how to implement an AJAX call that would allow the user to search for a new query term and reload the map. When I click the search box, the keyword alerts that the keyword is the text in the search box. But the map does not update based on the new keyword.
So I have as a JS script:
var map;
var pointsLayer;
var markerMap = {};
var keyword; //instantiating keyword for global scope
$(document).ready(function(){
map = new L.Map('mapContainer');
var url = 'http://{s}.tiles.mapbox.com/v3/mapbox.mapbox-streets/{z}/{x}/{y}.png';
var copyright = 'Map data © 2011 OpenStreetMap contributors, Imagery © 2011 CloudMade';
var tileLayer = new L.TileLayer(url, {attribution:copyright});
//var startPosition = new L.LatLng(42.33143, -83.04575);//detroit
var startPosition = new L.LatLng(41.883333, -87.633333);//chicago
//var startPosition = new L.LatLng(40.7143528, -74.0059731);//new york
map.on('load', function(){
keyword = 'history'; //setting keyword to history on first load
requestUpdatedPoints();
keyword = ''; //clearing keyword after first load
});
map.setView(startPosition, 13).addLayer(tileLayer);
map.on('moveend', function(){
requestUpdatedPoints();
});
//////////////
/// WRONG ADDITION OF ADDING KEYWORD SEARCH?
//////////////
$('a#submitSearch').on('click', function(e, keyword){
e.preventDefault();
//keyword = '';
keyword = $('input#keyword').val(); //setting keyword to whatever is in the search box
alert(keyword); //did it set it?
requestUpdatedPoints(keyword); //send in new AJAX call with new keyword
location.reload();
});
});
function requestUpdatedPoints(keyword){
$.ajax({
type: 'GET',
url: 'http://api.infochimps.com/encyclopedic/wikipedia/dbpedia/wikipedia_articles/search?g.radius=100000&g.latitude=41.883333&g.longitude=-87.633333&f.q='+this.keyword+'&apikey=api_test-W1cipwpcdu9Cbd9pmm8D4Cjc469',
dataType: 'jsonp',
//data: JSON.stringify(data),
contentType: 'application/json; charset=utf-8',
success: function(result){
for( var i=0; i<result.results.length - 1; i++ ){
console.log("adding " + result.results[i].wikipedia_id + " to the map")
var marker = L.marker([result.results[i].coordinates[1], result.results[i].coordinates[0]]).addTo(map);
marker.bindPopup(''+result.results[i].wikipedia_id+'');
}
},
error: function(){
alert('check your error log.');
}
});
}
the HTML is:
<!DOCTYPE html>
<html>
<head>
<link rel="stylesheet" href="./style.css">
<link rel="stylesheet" href="http://cdn.leafletjs.com/leaflet-0.4/leaflet.css">
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>
<script type="text/javascript" src="http://cdn.leafletjs.com/leaflet-0.4/leaflet.js"></script>
<script type="text/javascript" src="./map.js"></script>
</head>
<body>
<h1>WikiMap</h1>
<div id="mapContainer"></div>
<div id="infoContainer">
<div id="search">
<form id="searchForm">
<label>Keyword:</label>
<input type="text" id="keyword" name="keyword" placeholder="search by keyword"/>
<a id="submitSearch" href="#">search</a>
</form>
</div>
</div>
</body>
</html>
My Question (UPDATED): How do I get my keyword to change in the API URL Search Query based off of an AJAX Call (having a scope problem here) ?
I've finally figured that my layout is poor for accomplishing what I want to get done. Even if the keyword is updating, the map.on() load function is reverting everything back to the beginning. I've decided to use Backbone.js to help me organize my data flows.
var searchControl = L.esri.Geocoding.Controls.geosearch({
providers: [
new L.esri.Geocoding.Controls.Geosearch.Providers.MapService({
label: 'States and Counties',
url: 'http://sampleserver6.arcgisonline.com/arcgis/rest/services/Census/MapServer',
layers: [2, 3],
searchFields: ['NAME', 'STATE_NAME']
})
]
}).addTo(map);
I am using leaflet map search api by address but I find an autosuggestion searching api something that.

How to show the compiled css from a .less file in the browser?

What is the best way to show the resulting css from files compiled with less.js in the client.
In other words, how can i fill a div with the resulting css?
I need to display the result on the page, any way to do this?
THanks!
update
As already pointed out in the comments by #ertrzyiks you should replace less.parse with less.render for Less v 2.x:
var lessCode = '';
var xmlhttp = new XMLHttpRequest();
xmlhttp.onreadystatechange = function(){
if(xmlhttp.status == 200 && xmlhttp.readyState == 4){
var options = {}
lessCode = xmlhttp.responseText;
less.render(lessCode, options, function (error, output) {
if(!error) {
document.getElementById('lesscode').innerHTML = output.css;
}
else document.getElementById('lesscode').innerHTML = '<span style="color:red">' + error + '</span>';
});
}
};
xmlhttp.open("GET","important.less",true);
xmlhttp.send();
see also: How to detect and print changing variables LESS
But since Less v2:
In the browser, less.pageLoadFinished will be a promise, resolved when
less has finished its initial processing. less.refresh and
less.modifyVars also return promises.
When you compile filename.less the compiled CSS code has been inject in a style tag with id less:filename, so to get the compilled CSS code you can also use:
less.pageLoadFinished.then(
function() {
console.log(document.getElementById('less:filename').innerHTML);
}
);
Notice that the last example also applies the compiled CSS code on the page.
--end update
I expected that running something such as the following was possible:
<link rel="stylesheet/less" type="text/css" href="important.less">
<script src="less-1.7.3.js" type="text/javascript"></script>
<script>
css = less.tree.toCSS();
console.log(css);
</script>
unfortunately this does not work, but you can use the following code to get what you want:
<script src="less-1.7.3.js" type="text/javascript"></script>
<script>
var lessCode = '';
var xmlhttp = new XMLHttpRequest();
xmlhttp.onreadystatechange = function(){
if(xmlhttp.status == 200 && xmlhttp.readyState == 4){
lessCode = xmlhttp.responseText;
new(less.Parser)().parse(lessCode, function (e, tree) {
document.getElementById('lesscode').innerHTML = tree.toCSS().replace(/\n/g,"<br>");
});
}
};
xmlhttp.open("GET","important.less",true);
xmlhttp.send();
</script>
With in the body section of your HTML:
<div id="lesscode"></div>
See also: Combining two .less files in one and How to open a local disk file with Javascript?
I just use Chrome's Inspect Element.
Right click on the element CSS you are looking for, Right click and choose Inspect element. On the right you will find the compiled CSS in Styles. Hope it helps
You have two options to do this, Internet Explorer or Firefox.
Let's start with Firefox. If you install the web developer toolbar, you get a menu option that's labelled CSS. Clicking on this gives you a few options and if you choose View CSS, you are taken to a new tab that shows you all of the styles for the page, grouped by their location and you should see a section with the CSS that has been generated by LESS and dynamically applied to the elements.
IE also has a Web Developer option and if you use the toolbar to inspect an element, you can then use the short cut 'Ctrl + T' which will bring up the page source with the computed styles.
The Firefox solution is better, as you can see exactly which styles have been provided by LESS whereas IE just lumps it all together.
There is a third option, and that is to compile the CSS server side!