How to load a custom .pbf file in ngx-openlayers - javascript

I was able to load maps using the ngx-openlayers with the following code
<aol-map [width]="'100%'" [height]="'100%'">
<aol-view [zoom]="zoom">
<aol-coordinate [x]="5" [y]="45" [srid]="'EPSG:4326'"></aol-coordinate>
</aol-view>
<aol-layer-tile [opacity]="opacity">
<aol-source-osm></aol-source-osm>
</aol-layer-tile>
<aol-layer-vector [opacity]="opacity">
<aol-source-vector>
<aol-feature>
<aol-geometry-point>
<aol-coordinate [x]="5" [y]="45" [srid]="'EPSG:4326'"></aol-coordinate>
</aol-geometry-point>
<aol-style>
<aol-style-circle [radius]="10">
<aol-style-stroke [color]="'black'" [width]="width"></aol-style-stroke>
<aol-style-fill [color]="'green'"></aol-style-fill>
</aol-style-circle>
</aol-style>
</aol-feature>
<aol-feature>
<aol-geometry-point>
<aol-coordinate [x]="5.1" [y]="45.1" [srid]="'EPSG:4326'"></aol-coordinate>
</aol-geometry-point>
<aol-style>
<aol-style-icon [src]="'assets/marker.png'" [anchor]="[0.5, 1]" [anchorXUnits]="'fraction'" [anchorYUnits]="'fraction'" [scale]="0.1"
[anchorOrigin]="'top-left'">
</aol-style-icon>
</aol-style>
</aol-feature>
</aol-source-vector>
</aol-layer-vector>
</aol-map>
My issue is I want to load a custom map location that I have served on my local machine using MapTile server on http://localhost:8090/tileserver.php#trails/ol3 URL.
Now the XYZ URL from the above server is (http://localhost:8090/tileserver.php?/index.json?/trails/{z}/{x}/{y}.pbf)
How can I load this map using the ngx-openlayers packkage
I have tried to use this but it is not working
<aol-map [width]="'500px'" [height]="'300px'">
<aol-interaction-default></aol-interaction-default>
<aol-control-defaults></aol-control-defaults>
<aol-control-fullscreen></aol-control-fullscreen>
<aol-layer-tile>
<aol-source-osm></aol-source-osm>
<aol-source-xyz [url]="'http://localhost:8090/tileserver.php?/index.json?/trails/{z}/{x}/{y}.pbf'">
</aol-source-xyz>
</aol-layer-tile>
<aol-view [zoom]="12">
<aol-coordinate [x]="6.47" [y]="53.44" [srid]="'EPSG:4326'"></aol-coordinate>
</aol-view>
</aol-map>

So yeah I'm about to answer my own question cause it might help someone in the future.
The Basics
There are two broad classifications for maps from OSM (OpenStreetMap)
1.Raster Format: This one is the raster image (PNG, JPEG, SVG ...) tiles for the map. This format can be compressed and put it to .mbtiles format.
You can use tools like mbuilt to extract the contents into the tms, wsm or XYZ folder structure. This one is the easy and faster option.
Vector Format: This one is a Vector file format it can have multiple file type like .pbf inside it. It can also be compressed into a .mbtiles file. we need a tile server to render the contents of the vector files.
Tile server GL is a tile server to serve both vector/raster map files (mbtiles)
After solving the offline hosting issue, I have used a default leaflet.js package for angular and everything worked fine without an issue.
I used OpenMaptiles map files to host them using the tileserver-gl

Related

D3 library in R?

I am working with the "r2d3" library in R (https://www.rstudio.com/blog/r2d3-r-interface-to-d3-visualizations/) - as I understand, this library is intended to perform javascript based data visualizations in R.
I would like to try and run the following visualization in R : https://rstudio.github.io/r2d3/articles/gallery/bubbles/
I loaded the data into R:
library(r2d3)
library(ggraph)
data(flare)
Then, I copied the entire "bubbles.js" script into a new R Markdown editor and clicked "knit to html". Then, I got the following output:
Clearly, I am doing something wrong.
Can someone please show me how to fix this?
Thanks!
Note: I tried running the following code in R Console:
r2d3(data = flare, d3_version = 4, script = "bubbles.js")
And this is the error I got:
/../as I understand, this library is intended to perform javascript
based data visualizations in R /../
It's more of an interface for existing D3 visualizations.
https://rstudio.github.io/r2d3/index.html provides fairly good overview of the process, you should go through that first.
To get that gallery sample working, you first prepare a working directory where you have:
flare.csv
bubbles.js
Once you have made sure your working dir is the same where those files are (getwed() / setwd()), running
library(r2d3)
r2d3(data = read.csv("flare.csv"), d3_version = 4, script = "bubbles.js")
in console / script / rmd should render those bubbles.
Or you could just clone the repo and have all sample files including Rmd-s - https://github.com/rstudio/r2d3/tree/main/vignettes/gallery/bubbles
RStudio provides some support for D3 scripts, so you can also go through File > New File > D3 Script and paste the bubbles.js content there or open existing bubbles.js file. Assuming you have flare.csv file in working directory, you can click on a Preview to have it rendered in Viewer pane. That's what the
// !preview r2d3 data = read.csv("flare.csv"), d3_version = 4
line in js script header is there for.

Rails 7 importmap leaflet-css images path fix?

What I'd like to do:
I would like to have a leaflet layers control in my Rails 7 app.
What I get:
Leaflet works fine, but the control appears without the icon, like this:
and in the browser console I get this error:
GET http://my_ip/trial_models/undefined/layers.png 404 (Not Found)
and in my server log the error is presented like this:
Started GET "/trial_models/undefined/layers.png" for my_ip at 2022-03-30 06:50:43 +0000
ActionController::RoutingError (No route matches [GET] "/trial_models/undefined/layers.png"):
I've replaced the actual ip address with "my_ip". The 'undefined' is really there in the error messages.
How I did it:
First I created a Rails 7 app and imported leaflet like this:
./bin/importmap pin leaflet
./bin/importmap pin leaflet-css
I then created a TrialModel using standard rails g scaffold. I then added the following stimulus div in trail_models\show.html.erb :
<div data-controller="trialmap" data-trialmap-target="trial" style="height:600px" class="leaflet-container"></div>
I created \app\javascript\controllers\trialmap_controller.js with the following contents:
import { Controller } from "#hotwired/stimulus";
import "leaflet-css";
export default class extends Controller {
static targets = [ "trial" ]
connect(){
import("leaflet").then( L => {
this.map = L.map(this.trialTarget).setView([ 51.472814, 7.321673 ], 14);
var base_map = L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
attribution: '© OpenStreetMap | SwmmGo',
transparency: true,
opacity: 0.5
}).addTo(this.map);
var landMap = L.tileLayer('http://{s}.tile.thunderforest.com/landscape/{z}/{x}/{y}.png', {attribution: 'attributions'});
var layersControl = new L.Control.Layers({
"Street Map": base_map,
"Landscape": landMap
});
this.map.addControl(layersControl);
});
}
disconnect(){
this.map.remove()
}
}
What I've explored:
I tried downloading leaflet-css like this:
./bin/importmap pin leaflet-css --download
but same result.
I can see that there is a references background-image:url(images/layers.png); in the imported/ downloaded file vendor/javascript/leaflet-css.js. But there doesn't seem be any images folder anywhere like vendor/javascript/images/ or the like.
The stringify version of L.Control.prototype.options is just {"position":"topright"}.
I tried setting L.Control.prototype.options.iconUrl = "layers.png" (and "/layers.png") in the js controller and then placing a manually downloaded layers.png file in public. But this changed neither the results nor the error messages.
My questions:
How can I get the icon to show and the error to disappear? (a work-around would be ok too)
What is the "correct way" to handle assets and asset paths which css files reference when using importmap?
Any help would be much appreciated! Thanks!
I had similiar problems when using markers, my solution was not using leaflet-css and just using the leaflet CSS from CDN
I did like Luis - put the leaflet.css downloaded from https://leafletjs.com in vendor/assets/stylesheets and the images in public/images - that solved my issues with broken marker/layer images
Don't use leaflet-css, it bundles both the leaflet css and an ancient version (0.6.4) of the leaflet js code. It seems that the other answers here are on target - rails importmaps are for js only; if you are working with a third-party lib that has its own css assets you will need to handle those separately either through a CDN or by downloading them and placing them alongside your other css assets.

Mapbox-gl Hosted S3 - addsource

I am working on this project where I want to add relatively dynamic data (updating every 15minutes) to a mapbox-gl via a serverless solution. I followed this excellent guide on creating serverless vector tiles and have the base tiles working.
My question is now how would you achieve adding a geojson point layer to the map (hosted on a simple HTML page), using something like:
var map = new mapboxgl.Map({
container: 'map',
style: style: "https://{domain}/bright.json",
});
var url = 'https://{domain}/geojsonfile.json'
map.addSource('geojsonfile', {
'type': 'geojson',
'data': url
});
map.addLayer({
'id': 'geojsonfile',
'type': 'symbol',
'source': 'geojsonfile',
'layout': {
'icon-image': 'rocket-15'
}
});
In a serverless vector environment without using Tippecanoe to convert the json file into protobuf vector tiles and instead adding the layer direct to the map from the javascript file. The above js for addsource and addlayer come from this Mapbox guide.
I can get the above js working when I pass in a mapboxgl.accessToken instead of self-hosting; however that's as far as I have been able to get. The geojson file is hosted in a CORS enabled s3 bucket.
Is the issue with loading in the source or displaying the layer? I have also tried modifying the bright.json file to handle the source and layer so that I only have to replace the s3 file, however have had no luck.
Any and all help / suggestions are much appreciated.
After quite a lot of blind trial and error, finally figured out a solution. Turns out my original script was trying to load the layer to the map on-load. However, the tile base load is configured via the style and tile files pre-load.
Therefore, the js addSource needs to be added to the map post-load and then style on-load.
this.map.on('style.load', function () {
this.pastInitialLoad = true;
this.map.addSource("geojsonfile", {
"type": "geojson",
"data": url }
);
If anyone else is stuck, these guides / sources were of great help!
https://schwanksta.com/blog/vector-tiles-introduction-pt1
http://fuzzytolerance.info/blog/2016/03/16/Leaflet-to-Mapbox-GL/
https://github.com/mapbox/mapbox-gl-js/issues/2268

pdf.js by andreasgal does not load pdf using absolute path. Works only with relative paths

I am using a javascript library to renders pdf files using a browser.
This is the one:
https://github.com/mozilla/pdf.js
I cannot get it working with absolute paths as the path to the PDF I want to display. Altough relative paths works fine.
This call does not work:
PDFView.open("D:/Projects/Empenho/Pdf1.pdf", 0);
With relative path I managed to have it working properly:
PDFView.open("https://localhost/MyPDFs/Pdf1.pdf", 0);
open() function:
function getDocument(source) {
var workerInitializedPromise, workerReadyPromise, transport;
if (!source.url)
error('Invalid parameter array, need either .data or .url');
workerInitializedPromise = new PDFJS.Promise();
workerReadyPromise = new PDFJS.Promise();
transport = new WorkerTransport(workerInitializedPromise, workerReadyPromise);
console.log(workerReadyPromise);
workerInitializedPromise.then(function transportInitialized() {
transport.fetchDocument(source);
});
return workerReadyPromise;
};
As long the system has not a good debug system nor a good documentation I can´t find out where the problem lies.
I believe there is somenthing related to the workerReadyPromise as I can print the object and see differences when using absolte x relative path.
When I use absolute path the workerReadyPromise state is that:
http://pbrd.co/10VGnuQ
Any Idea?
PS. I am not sure if this is the same case, but found this:
Loading a pdf document using absolute path
It seems that pdf.js, gets the file you specify using AJAX.
You cannot use local file paths for AJAX requests and that seems to be where you are having problems
The answer to this question explains why.

random images from a folder

I am trying to rewrite my code below to search a folder for all the images (they will be numbered but there maybe gaps, ie not 1.jpg,2.jpg,3.jpg but instead 1.jpg,15.jpg,60.jpg for this reason i would like to search the folder, put all the images into an array and then pick one randomly each time its looped.
Any help would be greatly appreciated.
Firstly i am currently specifying image total above the main script below:
imgWidth = 160,
imgHeight = 95,
imgTotal = 22,
total = 0,
tiles;
//create the HTML for the tiles and append that to the bg element
function makeTiles(count){
var html = '', imgNum;
while(count--){
imgNum = Math.floor(Math.random()*imgTotal + 1);
html += "<div class='tile' style='background:url(public/images/portfolio/all/"+imgNum+".jpg) 0 0 no-repeat;' ><img style='opacity:0; filter:alpha(opacity=0);' src='public/images/portfolio/all/"+imgNum+"-c.jpg' alt='' /></div>\r";
}
$bg.append(html);
}
You'll need to create a list of available images with something else than javascript, since it has no filesystem access, even though in the end, you are accessing the images via their url.
Workaround: enable some directory listing for the images, then access this page via javascript, parse the image files and construct an array out of them; but frankly, there are shorter and more robust ways to accomplish this ...
pseudocode ..
$ ls -1 *jpg > imagesfilelist.txt
$ cp imagefilelist.txt /some/publicly/accessible/folder
js/jquery ..
$.get("/some/publicly/accessible/folder/imagefilelist.txt", function(data){
alert("My image files: " + data);
});
...
javascript can not access local folders. point.
I repeat: there is no way you can "search folder" to get "array of images" in JS. You could do that part (server only!) in PHP or such server-side language and return results via AJAX.
To do what you want you need to know what the images are called. JavaScript cannot access folder directly as commented above. You would need to use a server side script to provide an array of the images for the JS to pick at random to do this.
Javascript will not be able to browse folders. What you need to do is to create an array of available images and then select a random one. You could do this using any server side technology (php, rails, java, .net ...).
The way you're trying to do it is a wrong one.But iwth a bit of tricks it could work though, but it's very wrong way to do this kind of things.
You can generate file list with php and feed it to your script. You can even create php script which will generate your script already populated with needed data but it's not the best to do this too.
So, the best ways are:
- create html with list of filenames/images(visible or invisible) by php, then manipulate it by javascript;
- create html and javascript wich will do AJAX query to php script which will return filename list(formated as JSON if you wish).
Why not upload your images to a free hosting site (like Flickr) grab the feed from your image group and select the random image from there?

Categories

Resources