How to use inner camera in gltf in aframe? - camera

I have a gltf model, which contains cameras, models and camera animations. After loading, they become an gltf entity. I can't use secondcamera el. SetAttribute ('camera ','active', true ')" to change camera. How can I use the camera in it.
This can be modified in three. JS
this.content.traverse((node) => {
if (node.isCamera && node.name === name) {
this.activeCamera = node;
}
});
this.renderer.render( this.scene, this.activeCamera )
but, how to use inner camera in gltf in aframe?

You could keep the reference to the camera:
var model_camera = null;
// wait until the model is loaded
entity.addEventListener("model-loaded", e => {
const mesh = entity.getObject3D("mesh");
mesh.traverse(node => {
// assuming there is one camera
if (node.isCamera) model_camera = node;
})
})
and when you need to use it, just substitute the active camera in the scene.camera property:
entity.sceneEl.camera = model_camera;
Check it out in this example with a model containing two different cameras.
Afaik there is no cleanup involved, the look-controls or wasd-controls will still be working as long as you don't manually disable them when switching cameras.
The camera system has a function for swapping active cameras, but you would need to add <a-entity> wrappers for the camera references (as the system tries to perform getObject3D('camera') on the provided entity).

Related

In React Native / Expo, is there any way to save a specific part of an image?

From some research, I've figured out that expo libraries like takePicturesAsync() are able to take a picture and save it to the app's cache. However, the default state for libraries like these is to save the whole image. Is there any way for me to save a specific part of the image (e.g. the 2500 pixels at the center of the screen)?
Thanks!
You can use the onPictureSaved event to grab & manipulate the image.
takePicture = () => {
if (this.camera) {
this.camera.takePictureAsync({ onPictureSaved: this.onPictureSaved });
}
};
onPictureSaved = photo => {
console.log(photo);
}

lazyloading swiper.js preloading the next image?

Is there a way to preload the next or two next images with a swiper.js while lazyloading is active?
The slider contains 100 images which we don’t want to load while the page opens for obvious reasons but we want the first and the two next images to be loaded to have them present within the next slide while the animation runs.
any ideas?
I am looking for the same thing, and looking at the swiperJS documentation, I stumbled upon the API settings for lazyloading.
Looks like maybe loadPrevNext and loadPrevNextAmount might help us out.
loadPrevNext (boolean, default:false)
Set to true to enable lazy loading for the closest slides images (for previous and next slide images)
(I think they actually mean preload next and previous image, if I check other examples and demo's)
loadPrevNextAmount (number, default: 1)
Amount of next/prev slides to preload lazy images in. Can't be less than slidesPerView
So:
const swiper = new Swiper('.swiper-container', {
lazy: {
loadPrevNext: true, // pre-loads the next image to avoid showing a loading placeholder if possible
loadPrevNextAmount: 2 //or, if you wish, preload the next 2 images
},
});
Since version 9, Swiper does not have a lazy loading API and instead leverages browsers' native lazy loading functionality:
Since version 9 Swiper doesn't have specifid lazy loading API, as it relies on native browser lazy loading feature. To use lazy loading, we just need to set loading="lazy" on images and add preloader element
loadPrevNextAmount is gone from the API. One way to achieve similar behavior is to use the slideChange event to force the next N images to load by setting their loading attribute to eager (assuming they were originally set as lazy and each slide element has a single image you want to preload):
const swiper = new Swiper('.swiper', { ... });
const preloadNext = (n) => {
swiper
.slides
.slice(swiper.activeIndex, swiper.activeIndex + n + 1)
.map(slide => slide.querySelector('img'))
.forEach(s => s.setAttribute('loading', 'eager'));
};
// preload the next 2 images immediately
preloadNext(2);
// preload the next 2 images after changing slides
swiper.on('slideChange', () => preloadNext(2));
Another possible optimization is to wait for the page to fully load, which includes the first image in the swiper, and only then preload the following images. This avoids loading the first 3 images at the same time in order to display the first image faster:
let swiper;
const preloadNext = (n) => {
swiper
.slides
.slice(swiper.activeIndex, swiper.activeIndex + n + 1)
.map(slide => slide.querySelector('img'))
.forEach(s => s.setAttribute('loading', 'eager'));
};
document.addEventListener('DOMContentLoaded', () => {
swiper = new Swiper('.swiper', { ... });
swiper.on('slideChange', () => preloadNext(2));
});
window.addEventListener('load', () => {
preloadNext(2);
});

Layout centered on one node

Is there a way to require that a layout doesn't change the position of one "root" node while considering it during the algorithm ? Or equivalently, is there a way to always center the camera to this node/keep the camera at the same relative position to this node ?
A bit of context. I am working on an iteratively built graph. Each time parts are added to the graph, the layout is completed. The graph may grow too big to be printed on a screen, and alternatives to the fit options are welcome. What is important though, is that the user is able to follow the node he selected. The best would be that this node doesn't move.
Here is an outline of the general approach. It can be applied with whatever strategy you like re. zoom and pan. The main thing is that you need to know the start and end positions of each node. So you run the layout in a batch, creating a visual nop, and then run a preset layout with the desired zoom and pan.
const clone = obj => Object.assign({}, obj);
const savePos1 = n => n.scratch('_layoutPos1', clone(n.position()));
const savePos2 = n => n.scratch('_layoutPos2', clone(n.position()));
const restorePos1 = n => n.position(n.scratch('_layoutPos1'));
const getPos2 = n => n.scratch('_layoutPos2');
cy.startBatch();
const nodes = cy.nodes();
const layout = cy.layout(myLayoutOptions); // n.b. animate:false
const layoutstop = layout.promiseOn('layoutstop');
nodes.forEach(savePos1);
layout.run();
await layoutstop;
nodes.forEach(savePos2);
nodes.forEach(restorePos1);
cy.endBatch();
cy.layout({
name: 'preset',
animate: true,
positions: getPos2,
// specify zoom and pan as desired
zoom,
pan
}).run();

Using multiple USB cameras with Web RTC

I want to use multiple USB camera with Web RTC.
For ex)
https://apprtc.appspot.com/?r=93443359
This application is web RTC sample.
I can connect to another machine, but I have to disconnect once to change the camera.
What I want to is,
1.Use two camera at the same time on the same screen.
2.(if 1 is not possible),I want to switch the camera without disconnecting current connection
Does anyone have information about how to use two camera on Web RTC?
call getUserMedia twice and change the camera input in between
You can use constraints to specify which camera to use and you can have both of them displayed in one page as well. To specify which camera to use take a look at the following snippet (only works on Chrome 30+):
getUserMedia({
video: {
mandatory: {
sourceId: webcamId,
...
}
},
successCallback,
failCallback);
The webcamId you can get by:
MediaStreamTrack.getSources(function(sources){
var cams = _.filter(sources, function(e){ //only return video elements
return e.kind === 'video';
});
var camIds = _.map(cams, function (e) { // return only ids
return e.id;
});
});
In the snippet above I've used underscore methods filter and map.
More information on:
WebRTC video sources
constraints

How to animate Google Maps API KML Ground Overlay

Two questions:
What is the best way to create a smooth animation through 12 KML Files through google maps API V2?
How can I integrate a fadeIn() / fadeOut() to smoothly transtition between these KML files?
I have experimented some with setTimeouts() with 2 of my KML filed but haven't figured out a smooth or consistent way to animate between them. Code is below.
function animate () {
function series_1 () {
geoXml = new GGeoXml("lake/colors_test.kml");
map.addOverlay(geoXml);
setTimeout("map.removeOverlay(geoXml)", 5000);
}
function series_2 () {
geoXml1 = new GGeoXml("lake/colors_test_1.kml");
map.addOverlay(geoXml1);
setTimeout("map.removeOverlay(geoXml1)", 5000);
}
series_1();
series_2();
}
animate();
I think you'll need to apply fading to the underlying images:
$("#mapContent").find("img[src*=\"lyrs=kml\"]").fadeOut();
This is for the V3 API, you might need a different selector for the V2 API.
I'm assuming the map is created with
map = new google.maps.Map document.getElementById("mapContent");
jQuery also has a fadeIn() method, however it gets tricky because the images are probably recreated when you add a new KML layer. You'll need to find a way to set their visibility to zero when they are created.