How to tell if Geotools map is in Pan Mode (Pan Tool Active) - geotools

Looking for a way to figure out if the current selected tool is the pan tool, or for that matter any specific tool.

In the Swing implementations inherited from org.geotools.swing.AbstractMapPane you may call getCursorTool() and check for the type of the returned value:
AbstractMapPane pane = ...
if (pane.getCursorTool() instanceof org.geotools.swing.tool.PanTool) {
// pan tool active
}
In the current SWT implementation org.geotools.swt.SwtMapPane it's not possible. Inherit from this class and override setCursorTool(CursorTool) to store a reference to the current tool.

Related

Is it possible to set snap settings?

I'm using the Autodesk Forge viewer v7 using the Edit2D tool. This question is specifically about the snapping functionality. It is currently working but a bit overzealous... It seems to have all of the possible snaps on (endpoint, along line, intersections, centers, etc.). It also seems to snap to layers that I have hidden.
Is there a way to set the snaps that are on and off? Also is there a way to limit the layers that it snaps to? I was looking for possibly a method that will tell me the object(s) it's trying to snap to and the type of snap and let me determine if that's a viable snap point and return true/false or something like that but I couldn't find one. Is there a way to do this?
EDIT
I did find setSnapFilter but it doesn't seem to do anything. I have this implementation in my code:
// #ts-ignore
e.defaultContext.snapper.sheetSnapper.setSnapFilter((e) => {
console.log(e);
return false;
});
However, I never get a console log happening. I have tried this on both the sheet snapper and the layer snapper and I've tried returning both true and false and none of them are ever called or make any difference to the snapping.
Good catch! The context.snapper.sheetSnapper object does have a setSnapFilter method you can override. Unfortunately, this filter is only invoked in the Snapper#onMouseMove method, and the Edit2D extension bypasses this method. That's why overriding the method has no effect. Let me pass this info to the engineering team for consideration.

How to do Plain Select

I'm using the Autodesk Forge Viewer with the Edit2D tools to allow the user to draw and modify polygons. I have this working with the polygonTool and polyEditTool. However, I also have a use case where the user needs to be able to select polygons but NOT make any modifications. As far as I can tell, the polyEditTool and moveTool allow the user to select polygons but they also allow them to modify. If I deactivate all tools they can't select, and the standard viewer selection doesn't seem to allow you to select the Edit2D shapes.
How can I get a selection only mode?
The Edit2D extension does not have any built-in option to only enable selection but not editing of shapes, and the workaround you suggested earlier looks reasonable.
Another option to consider would be implementing a custom subclass of EditToolBase (you could use the implementation of the official Edit2D tools as a reference) that would only allow selection, and nothing else.
Ok well it seems a little convoluted but I found a way that seems to work. The move tool allows you to select and move, but each shape has a movable property. If you set movable to false on the shape it can still be selected but can't be moved. So if you are switching between the editing and selection only modes you would have to change that property by iterating over the shapes on the layer and set it each time. Here is my implementation:
for (const shape of state.editor.defaultContext.layer.shapes) {
// #ts-ignore
shape.movable = tool !== DrawTools.Select;
}
Note that TypeScript definitions don't seem to include the movable property so I have to ignore the error.
This seems to work but if there is a better solution out there I would be happy to accept a better answer.

Autodesk forge transform extension turn on / off X, Y, Z axes

i'm using the transform extension. Sometimes I want the x, y and z axes to be closed. For example, in this three.js example, pressing the x, y or z keys can be opened and closed via a feature such as .showX. When I try this in the forge extension, there is no such feature. What can I do about it.
I am simply writing such code here. Console log is written, but the axis are still visible.
document.addEventListener('keydown', function (event) {
if (event.key === "x") {
console.log("X press");
_transformControlTx.showX = !_transformControlTx.showX;
}
if (event.key === "y") {
console.log("Y press");
_transformControlTx.showY = !_transformControlTx.showY;
}
if (event.key === "z") {
console.log("Z press");
_transformControlTx.showZ = !_transformControlTx.showZ;
}
});
This question has been discussed on Forge accelerator last week. The discussion is copied here for reference:
Xiaodong:
The transform tool is based on THREE.TransformControls. In the new version of TRHEE.js, it looks it supports handling visibility of the axis, but since Forge Viewer is packaged from old version of three.js, I am afraid it does not support yet. copied my colleagues #Varun Patil - Forge Team, #Petr Broz (Forge Team) (because of time diff, it may take some time they comment).
it seems one more workaround from community: Three.js Transform Controls - How to show only two arrows
Eason:
I compared two TransformControls between three.js example and Forge viewer’s. Unfortunately, they are totally different one. Forge Viewer’s TransformControls is based on three.js r71, so it doesn’t have the direct showing/hiding axises support. You need to do that as the Stack Overflow thread above does.
Petr:
I’m afraid that the transform tool from three.js might be manipulating the scene graph during runtime, adding and removing 3D objects as needed… that would explain why your modifications don’t seem to stick. in general, if you need to modify some component of three.js that is not extensible, instead of fighting with the implementation I’d probably suggest building your own… if all you need is a movement in X or Y, you could just have a 3D object with two thin cylinders, red and green, and handle their mouseover, mousedown, mousemove, and mouseup events

how to change a CesiumJS viewer's baselayer url

i am using a CesiumJS instance to display a base map of the earth using a imageryProvider from source A.
var viewer = new Cesium.Viewer('cesiumContainer', imageryProvider:providerA);
Now while using the Viewer I would like to be able to change this map to get images from providerB at a certain event.
I tried:
viewer.scene.imageryLayers.get(0).imageryProvider.url = providerB.url
However that does not seem to work and also feels quite like hack anyway.
I could not find anything in Cesium's documentation .
Is this at all possible without restarting / recreating the viewer instance?
I know that there is a Cesium.BaseLayerPicker (https://cesium.com/docs/cesiumjs-ref-doc/BaseLayerPicker.html)
However I do not see what method this picker calls on "select" )
Thanks a lot.
The BaseLayerPicker widget calls this code when the user selects a new layer.
There's a lot of boilerplate widget management in that block of code, but for your sake, only a couple of the lines are critical. First, the old existing active imagery layer is searched for, and removed:
imageryLayers.remove(layer);
Then, a new imagery provider is constructed and added at index 0, the first position, which is the base imagery layer:
imageryLayers.addImageryProvider(newProviders, 0);
You can directly change the URL of the provider but you should also change appropriate parameters("layers" in case of WMS, "layer", "style", "format", "tileMatrixSetID " ... in case of WMTS) depending on the type of provider(WMS or WMTS).

How to use the Selection Reticle in CesiumJS

In any of the Cesium sandcastle examples with entities, clicking an entity shows a green square reticle type thing.
My question is, what is it? I want to implement something that behaves similarly but can't find anything about it in the code base or the documentation.
Note: I have disabled the selection widget in my application.
You can see the reticle thing I am talking about in the attached photo.
You mention:
Note: I have disabled the selection widget in my application.
I'm guessing you have a typo or something, because that green reticle is indeed the SelectionIndicator. It can be disabled by setting a constructor option on the Cesium.Viewer, namely:
var viewer = new Cesium.Viewer('cesiumContainer', {
selectionIndicator: false
});
Check your code to see if you really set this option correctly in the constructor.
After the viewer is constructed, it's a bit late to try to turn it off, since it binds into events generated by viewer.selectedEntity changing values. By default, the selectedEntity gets the SelectionIndicator unless the viewer was constructed without one.