com.jme3.terrain.Terrain

Here are the examples of the java api com.jme3.terrain.Terrain taken from open source projects. By voting up you can indicate which examples are most useful and appropriate.

63 Examples 7

19 Source : TerrainTestReadWrite.java
with Apache License 2.0
from neuroph

/**
 * Saves and loads terrain.
 *
 * @author Brent Owens
 */
public clreplaced TerrainTestReadWrite extends SimpleApplication {

    private Terrain terrain;

    protected BitmapText hintText;

    private float grreplacedScale = 64;

    private float dirtScale = 16;

    private float rockScale = 128;

    private Material matTerrain;

    private Material matWire;

    public static void main(String[] args) {
        TerrainTestReadWrite app = new TerrainTestReadWrite();
        app.start();
    // testHeightmapBuilding();
    }

    @Override
    public void initialize() {
        super.initialize();
        loadHintText();
    }

    @Override
    public void simpleInitApp() {
        createControls();
        createMap();
    }

    private void createMap() {
        matTerrain = new Material(replacedetManager, "Common/MatDefs/Terrain/TerrainLighting.j3md");
        matTerrain.setBoolean("useTriPlanarMapping", false);
        matTerrain.setBoolean("WardIso", true);
        // ALPHA map (for splat textures)
        matTerrain.setTexture("AlphaMap", replacedetManager.loadTexture("Textures/Terrain/splat/alphamap.png"));
        // HEIGHTMAP image (for the terrain heightmap)
        Texture heightMapImage = replacedetManager.loadTexture("Textures/Terrain/splat/mountains512.png");
        // GRreplaced texture
        Texture grreplaced = replacedetManager.loadTexture("Textures/Terrain/splat/grreplaced.jpg");
        grreplaced.setWrap(WrapMode.Repeat);
        matTerrain.setTexture("DiffuseMap", grreplaced);
        matTerrain.setFloat("DiffuseMap_0_scale", grreplacedScale);
        // DIRT texture
        Texture dirt = replacedetManager.loadTexture("Textures/Terrain/splat/dirt.jpg");
        dirt.setWrap(WrapMode.Repeat);
        matTerrain.setTexture("DiffuseMap_1", dirt);
        matTerrain.setFloat("DiffuseMap_1_scale", dirtScale);
        // ROCK texture
        Texture rock = replacedetManager.loadTexture("Textures/Terrain/splat/road.jpg");
        rock.setWrap(WrapMode.Repeat);
        matTerrain.setTexture("DiffuseMap_2", rock);
        matTerrain.setFloat("DiffuseMap_2_scale", rockScale);
        Texture normalMap0 = replacedetManager.loadTexture("Textures/Terrain/splat/grreplaced_normal.jpg");
        normalMap0.setWrap(WrapMode.Repeat);
        Texture normalMap1 = replacedetManager.loadTexture("Textures/Terrain/splat/dirt_normal.png");
        normalMap1.setWrap(WrapMode.Repeat);
        Texture normalMap2 = replacedetManager.loadTexture("Textures/Terrain/splat/road_normal.png");
        normalMap2.setWrap(WrapMode.Repeat);
        matTerrain.setTexture("NormalMap", normalMap0);
        matTerrain.setTexture("NormalMap_1", normalMap2);
        matTerrain.setTexture("NormalMap_2", normalMap2);
        matWire = new Material(replacedetManager, "Common/MatDefs/Misc/Unshaded.j3md");
        matWire.getAdditionalRenderState().setWireframe(true);
        matWire.setColor("Color", ColorRGBA.Green);
        // CREATE HEIGHTMAP
        AbstractHeightMap heightmap = null;
        try {
            heightmap = new ImageBasedHeightMap(heightMapImage.getImage(), 1f);
            heightmap.load();
        } catch (Exception e) {
            e.printStackTrace();
        }
        if (new File("terrainsave.jme").exists()) {
            loadTerrain();
        } else {
            // create the terrain as normal, and give it a control for LOD management
            // , new LodPerspectiveCalculatorFactory(getCamera(), 4)); // add this in to see it use entropy for LOD calculations
            TerrainQuad terrainQuad = new TerrainQuad("terrain", 65, 129, heightmap.getHeightMap());
            TerrainLodControl control = new TerrainLodControl(terrainQuad, getCamera());
            // patch size, and a multiplier
            control.setLodCalculator(new DistanceLodCalculator(65, 2.7f));
            terrainQuad.addControl(control);
            terrainQuad.setMaterial(matTerrain);
            terrainQuad.setLocalTranslation(0, -100, 0);
            terrainQuad.setLocalScale(4f, 0.25f, 4f);
            rootNode.attachChild(terrainQuad);
            this.terrain = terrainQuad;
        }
        DirectionalLight light = new DirectionalLight();
        light.setDirection((new Vector3f(-0.5f, -1f, -0.5f)).normalize());
        rootNode.addLight(light);
    }

    /**
     * Create the save and load actions and add them to the input listener
     */
    private void createControls() {
        flyCam.setMoveSpeed(50);
        cam.setLocation(new Vector3f(0, 100, 0));
        inputManager.addMapping("save", new KeyTrigger(KeyInput.KEY_T));
        inputManager.addListener(saveActionListener, "save");
        inputManager.addMapping("load", new KeyTrigger(KeyInput.KEY_Y));
        inputManager.addListener(loadActionListener, "load");
        inputManager.addMapping("clone", new KeyTrigger(KeyInput.KEY_C));
        inputManager.addListener(cloneActionListener, "clone");
    }

    public void loadHintText() {
        hintText = new BitmapText(guiFont, false);
        hintText.setSize(guiFont.getCharSet().getRenderedSize());
        hintText.setLocalTranslation(0, getCamera().getHeight(), 0);
        hintText.setText("Hit T to save, and Y to load");
        guiNode.attachChild(hintText);
    }

    private ActionListener saveActionListener = new ActionListener() {

        public void onAction(String name, boolean pressed, float tpf) {
            if (name.equals("save") && !pressed) {
                FileOutputStream fos = null;
                try {
                    long start = System.currentTimeMillis();
                    fos = new FileOutputStream(new File("terrainsave.jme"));
                    // we just use the exporter and preplaced in the terrain
                    BinaryExporter.getInstance().save((Savable) terrain, new BufferedOutputStream(fos));
                    fos.flush();
                    float duration = (System.currentTimeMillis() - start) / 1000.0f;
                    System.out.println("Save took " + duration + " seconds");
                } catch (IOException ex) {
                    Logger.getLogger(TerrainTestReadWrite.clreplaced.getName()).log(Level.SEVERE, null, ex);
                } finally {
                    try {
                        if (fos != null) {
                            fos.close();
                        }
                    } catch (IOException e) {
                        Logger.getLogger(TerrainTestReadWrite.clreplaced.getName()).log(Level.SEVERE, null, e);
                    }
                }
            }
        }
    };

    private void loadTerrain() {
        FileInputStream fis = null;
        try {
            long start = System.currentTimeMillis();
            // remove the existing terrain and detach it from the root node.
            if (terrain != null) {
                Node existingTerrain = (Node) terrain;
                existingTerrain.removeFromParent();
                existingTerrain.removeControl(TerrainLodControl.clreplaced);
                existingTerrain.detachAllChildren();
                terrain = null;
            }
            // import the saved terrain, and attach it back to the root node
            File f = new File("terrainsave.jme");
            fis = new FileInputStream(f);
            BinaryImporter imp = BinaryImporter.getInstance();
            imp.setreplacedetManager(replacedetManager);
            terrain = (TerrainQuad) imp.load(new BufferedInputStream(fis));
            rootNode.attachChild((Node) terrain);
            float duration = (System.currentTimeMillis() - start) / 1000.0f;
            System.out.println("Load took " + duration + " seconds");
            // now we have to add back the camera to the LOD control
            TerrainLodControl lodControl = ((Node) terrain).getControl(TerrainLodControl.clreplaced);
            if (lodControl != null)
                lodControl.setCamera(getCamera());
        } catch (IOException ex) {
            Logger.getLogger(TerrainTestReadWrite.clreplaced.getName()).log(Level.SEVERE, null, ex);
        } finally {
            try {
                if (fis != null) {
                    fis.close();
                }
            } catch (IOException ex) {
                Logger.getLogger(TerrainTestReadWrite.clreplaced.getName()).log(Level.SEVERE, null, ex);
            }
        }
    }

    private ActionListener loadActionListener = new ActionListener() {

        public void onAction(String name, boolean pressed, float tpf) {
            if (name.equals("load") && !pressed) {
                loadTerrain();
            }
        }
    };

    private ActionListener cloneActionListener = new ActionListener() {

        public void onAction(String name, boolean pressed, float tpf) {
            if (name.equals("clone") && !pressed) {
                Terrain clone = (Terrain) ((Node) terrain).clone();
                ((Node) terrain).removeFromParent();
                terrain = clone;
                getRootNode().attachChild((Node) terrain);
            }
        }
    };

    // no junit tests, so this has to be hand-tested:
    private static void testHeightmapBuilding() {
        int s = 9;
        int b = 3;
        float[] hm = new float[s * s];
        for (int i = 0; i < s; i++) {
            for (int j = 0; j < s; j++) {
                hm[(i * s) + j] = i * j;
            }
        }
        for (int i = 0; i < s; i++) {
            for (int j = 0; j < s; j++) {
                System.out.print(hm[i * s + j] + " ");
            }
            System.out.println("");
        }
        TerrainQuad terrain = new TerrainQuad("terrain", b, s, hm);
        float[] hm2 = terrain.getHeightMap();
        boolean failed = false;
        for (int i = 0; i < s * s; i++) {
            if (hm[i] != hm2[i]) {
                failed = true;
            }
        }
        System.out.println("");
        if (failed) {
            System.out.println("Terrain heightmap building FAILED!!!");
            for (int i = 0; i < s; i++) {
                for (int j = 0; j < s; j++) {
                    System.out.print(hm2[i * s + j] + " ");
                }
                System.out.println("");
            }
        } else {
            System.out.println("Terrain heightmap building PreplacedED");
        }
    }
}

19 Source : TerrainLodControl.java
with Apache License 2.0
from neuroph

public void setTerrain(Terrain terrain) {
    this.terrain = terrain;
}

19 Source : PaintTest.java
with GNU Lesser General Public License v3.0
from huliqing

private void doSaveTerrain(Terrain terrain) {
    // 保存地形文件
    String terrainFullName = replacedetDir + terrainModelDir + "/" + terrainName + ".j3o";
    File terrainFile = new File(terrainFullName);
    try {
        BinaryExporter.getInstance().save((Spatial) terrain, terrainFile);
    } catch (IOException ex) {
        Logger.getLogger(PaintTest.clreplaced.getName()).log(Level.SEVERE, null, ex);
    }
}

19 Source : TexLayerTool.java
with GNU Lesser General Public License v3.0
from huliqing

public int getLayerCounts() {
    Terrain terrain = getTerrain();
    if (terrain == null)
        return 0;
    for (int i = 0; i < TerrainUtils.MAX_TEXTURES; i++) {
        if (TerrainUtils.getDiffuseTexture(terrain, i) == null) {
            return i;
        }
    }
    return 0;
}

19 Source : SmoothTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

@Override
public void undo() {
    if (undoLocs == null || undoHeights == null)
        return;
    Terrain terrain = getTerrain(selectObj);
    resetHeight(terrain, undoLocs, undoHeights);
}

19 Source : SmoothTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

@Override
public void redo() {
    Terrain terrain = getTerrain(selectObj);
    modifyHeight(terrain, worldLoc, radius, weight);
}

19 Source : SlopeTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

@Override
public void undo() {
    if (undoLocs == null || undoHeights == null)
        return;
    Terrain terrain = getTerrain(selectObj);
    resetHeight(terrain, undoLocs, undoHeights, precise);
}

19 Source : LevelTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

@Override
public void undo() {
    if (undoLocs == null || undoHeights == null)
        return;
    Terrain terrain = getTerrain(selectObj);
    resetHeight(terrain, undoLocs, undoHeights, precision);
}

18 Source : PaintTest.java
with GNU Lesser General Public License v3.0
from huliqing

/**
 * @author huliqing
 */
public clreplaced PaintTest extends SimpleApplication {

    private final float DEFAULT_TEXTURE_SCALE = 16.0625f;

    private String replacedetDir = "C:\\home\\workspace\\jme3.1\\luoying\\ly-editor\\replacedets";

    private final static String terrainModelDir = "/Models/terrains";

    private final static String terrainTextureDir = "/Textures/terrains";

    private String terrainName = "terrainTest";

    private Spatial terrainSpatial;

    private Terrain terrain;

    private Material mat;

    public static void main(String[] args) {
        PaintTest app = new PaintTest();
        app.start();
    }

    @Override
    public void simpleInitApp() {
        flyCam.setMoveSpeed(100);
        this.cam.setLocation(new Vector3f(0, 50, 30));
        this.cam.lookAt(new Vector3f(), Vector3f.UNIT_Y);
        try {
            // Terrain temp = TerrainUtils.doCreateTerrain(this, replacedetDir, terrainTextureDir, terrainName, 256, 64, 256, null, replacedetConstants.TEXTURES_TERRAIN_DIRT);
            // TerrainUtils.doSaveAlphaImages(temp, replacedetDir);
            // doSaveTerrain(temp);
            // terrain = (Terrain) replacedetManager.loadModel(terrainModelDir + "/" + terrainName + ".j3o");
            // terrain = TerrainUtils.doCreateTerrain(this, replacedetDir, terrainTextureDir, terrainName, 256, 64, 256, null, replacedetConstants.TEXTURES_TERRAIN_DIRT);
            terrain = (Terrain) replacedetManager.loadModel(terrainModelDir + "/" + terrainName + ".j3o");
        } catch (Exception ex) {
            Logger.getLogger(PaintTest.clreplaced.getName()).log(Level.SEVERE, null, ex);
        }
        terrainSpatial = (Spatial) terrain;
        rootNode.attachChild(terrainSpatial);
        rootNode.addLight(new AmbientLight());
        mat = terrain.getMaterial();
        // addTextureLayer(1);
        inputManager.addListener(new ActionListener() {

            @Override
            public void onAction(String name, boolean isPressed, float tpf) {
                if (isPressed)
                    return;
                PaintTerrainToolAction action = new PaintTerrainToolAction();
                action.paintTexture(terrain, new Vector3f(FastMath.nextRandomFloat() * 100.0f, 0, FastMath.nextRandomFloat() * 100.0f), 3, 3, 1);
            }
        }, "test");
        inputManager.addListener(new ActionListener() {

            @Override
            public void onAction(String name, boolean isPressed, float tpf) {
                if (isPressed)
                    return;
                TerrainUtils.doSaveAlphaImages(terrain, replacedetDir);
                doSaveTerrain(terrain);
            }
        }, "save");
        inputManager.addMapping("test", new MouseButtonTrigger(MouseInput.BUTTON_LEFT));
        inputManager.addMapping("save", new MouseButtonTrigger(MouseInput.BUTTON_RIGHT));
    }

    private void doSaveTerrain(Terrain terrain) {
        // 保存地形文件
        String terrainFullName = replacedetDir + terrainModelDir + "/" + terrainName + ".j3o";
        File terrainFile = new File(terrainFullName);
        try {
            BinaryExporter.getInstance().save((Spatial) terrain, terrainFile);
        } catch (IOException ex) {
            Logger.getLogger(PaintTest.clreplaced.getName()).log(Level.SEVERE, null, ex);
        }
    }

    public void addTextureLayer(int layer) {
        float scale = DEFAULT_TEXTURE_SCALE;
        setDiffuseTextureScale(layer, scale);
        setDiffuseTexture(layer, "Textures/grreplaced.jpg");
    }

    public void setDiffuseTextureScale(int layer, float scale) {
        terrain.getMaterial().setFloat("DiffuseMap_" + layer + "_scale", scale);
    }

    public void setDiffuseTexture(int layer, String texturePath) {
        Texture texture = getreplacedetManager().loadTexture(texturePath);
        texture.setWrap(Texture.WrapMode.Repeat);
        terrain.getMaterial().setTexture("DiffuseMap_" + layer, texture);
    }
}

18 Source : TerrainUtils.java
with GNU Lesser General Public License v3.0
from huliqing

public final static void setDiffuseTextureScale(Terrain terrain, int layer, float scale) {
    terrain.getMaterial().setFloat("DiffuseMap_" + layer + "_scale", scale);
}

18 Source : TerrainUtils.java
with GNU Lesser General Public License v3.0
from huliqing

public final static void removeDiffuseTexture(Terrain terrain, int layer) {
    if (layer == 0)
        terrain.getMaterial().clearParam("DiffuseMap");
    else
        terrain.getMaterial().clearParam("DiffuseMap_" + layer);
}

18 Source : TerrainUtils.java
with GNU Lesser General Public License v3.0
from huliqing

public final static void removeNormalTexture(Terrain terrain, int layer) {
    if (layer == 0)
        terrain.getMaterial().clearParam("NormalMap");
    else
        terrain.getMaterial().clearParam("NormalMap_" + layer);
}

18 Source : SmoothTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

private void modifyHeight(Terrain terrain, Vector3f worldLoc, float radius, float height) {
    // 消除地形的位置和旋转导致的偏移,但是不消除缩放,这们允许地形在缩放、旋转和移动后进行编辑。
    // 否则地形不能旋转和移动
    Spatial terrainSpaitla = (Spatial) terrain;
    Vector3f location = worldLoc.subtract(terrainSpaitla.getWorldTranslation());
    terrainSpaitla.getWorldRotation().inverse().mult(location, location);
    int radiusStepsX = (int) (radius / ((Node) terrain).getLocalScale().x);
    int radiusStepsZ = (int) (radius / ((Node) terrain).getLocalScale().z);
    float xStepAmount = ((Node) terrain).getLocalScale().x;
    float zStepAmount = ((Node) terrain).getLocalScale().z;
    List<Vector2f> locs = new ArrayList<Vector2f>();
    List<Float> heights = new ArrayList<Float>();
    for (int z = -radiusStepsZ; z < radiusStepsZ; z++) {
        for (int x = -radiusStepsX; x < radiusStepsX; x++) {
            float locX = location.x + (x * xStepAmount);
            float locZ = location.z + (z * zStepAmount);
            // see if it is in the radius of the tool
            if (ToolUtils.isInRadius(locX - location.x, locZ - location.z, radius)) {
                Vector2f terrainLoc = new Vector2f(locX, locZ);
                // adjust height based on radius of the tool
                float center = terrain.getHeightmapHeight(terrainLoc);
                float left = terrain.getHeightmapHeight(new Vector2f(terrainLoc.x - 1, terrainLoc.y));
                float right = terrain.getHeightmapHeight(new Vector2f(terrainLoc.x + 1, terrainLoc.y));
                float up = terrain.getHeightmapHeight(new Vector2f(terrainLoc.x, terrainLoc.y + 1));
                float down = terrain.getHeightmapHeight(new Vector2f(terrainLoc.x, terrainLoc.y - 1));
                int count = 1;
                float amount = center;
                if (!isNaN(left)) {
                    amount += left;
                    count++;
                }
                if (!isNaN(right)) {
                    amount += right;
                    count++;
                }
                if (!isNaN(up)) {
                    amount += up;
                    count++;
                }
                if (!isNaN(down)) {
                    amount += down;
                    count++;
                }
                // take average
                amount /= count;
                // weigh it
                float diff = amount - center;
                diff *= height;
                locs.add(terrainLoc);
                heights.add(diff);
            }
        }
    }
    undoLocs = locs;
    undoHeights = heights;
    // do the actual height adjustment
    terrain.adjustHeight(locs, heights);
    // or else we won't collide with it where we just edited
    ((Node) terrain).updateModelBound();
}

18 Source : SmoothTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

private void resetHeight(Terrain terrain, List<Vector2f> undoLocs, List<Float> undoHeights) {
    List<Float> neg = new ArrayList<Float>();
    for (Float f : undoHeights) neg.add(f * -1f);
    terrain.adjustHeight(undoLocs, neg);
    ((Node) terrain).updateModelBound();
}

18 Source : RoughTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

@Override
public void redo() {
    Terrain terrain = getTerrain(selectObj);
    roughen(terrain, worldLoc, radius, weight, params);
}

18 Source : RoughTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

@Override
public void undo() {
    Terrain terrain = getTerrain(selectObj);
    if (undoLocs == null || undoHeights == null)
        return;
    resetHeight(terrain, undoLocs, undoHeights);
}

18 Source : AbstractTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

/**
 * 从EnreplacedyControlTile中获取Terrain,如果不是Terrain类型的Enreplacedy,则返回null.
 * @param eso
 * @return
 */
protected Terrain getTerrain(EnreplacedyControlTile eso) {
    Spatial terrainSpatial = eso.getTarget().getSpatial();
    if (!(terrainSpatial instanceof Terrain)) {
        throw new IllegalStateException("terrainSpatial must be a Terrain object! eso=" + eso);
    }
    Terrain terrain = (Terrain) terrainSpatial;
    return terrain;
}

17 Source : TerrainLodControl.java
with Apache License 2.0
from neuroph

/**
 * Tells the terrain to update its Level of Detail.
 * It needs the cameras to do this, and there could possibly
 * be several cameras in the scene, so it accepts a list
 * of cameras.
 * NOTE: right now it just uses the first camera preplaceded in,
 * in the future it will use all of them to determine what
 * LOD to set.
 *
 * This control serializes, but it does not save the Camera reference.
 * This camera reference has to be manually added in when you load the
 * terrain to the scene!
 *
 * When the control or the terrain are removed from the scene, you should call
 * TerrainLodControl.detachAndCleanUpControl() to remove any threads it created
 * to handle the LOD processing. If you supply your own executor service, then
 * you have to handle its thread termination yourself.
 *
 * @author Brent Owens
 */
public clreplaced TerrainLodControl extends AbstractControl {

    private Terrain terrain;

    protected List<Camera> cameras;

    private List<Vector3f> cameraLocations = new ArrayList<Vector3f>();

    protected LodCalculator lodCalculator;

    // used when enabled is set to false
    private boolean hasResetLod = false;

    private HashMap<String, UpdatedTerrainPatch> updatedPatches;

    private final Object updatePatchesLock = new Object();

    // used for LOD calc
    protected List<Vector3f> lastCameraLocations;

    private AtomicBoolean lodCalcRunning = new AtomicBoolean(false);

    private int lodOffCount = 0;

    protected ExecutorService executor;

    protected Future<HashMap<String, UpdatedTerrainPatch>> indexer;

    private boolean forceUpdate = true;

    public TerrainLodControl() {
    }

    public TerrainLodControl(Terrain terrain, Camera camera) {
        List<Camera> cams = new ArrayList<Camera>();
        cams.add(camera);
        this.terrain = terrain;
        this.cameras = cams;
        // a default calculator
        lodCalculator = new DistanceLodCalculator(65, 2.7f);
    }

    /**
     * Only uses the first camera right now.
     * @param terrain to act upon (must be a Spatial)
     * @param cameras one or more cameras to reference for LOD calc
     */
    public TerrainLodControl(Terrain terrain, List<Camera> cameras) {
        this.terrain = terrain;
        this.cameras = cameras;
        // a default calculator
        lodCalculator = new DistanceLodCalculator(65, 2.7f);
    }

    @Override
    protected void controlRender(RenderManager rm, ViewPort vp) {
    }

    /**
     * Set your own custom executor to be used. The control will use
     * this instead of creating its own.
     */
    public void setExecutor(ExecutorService executor) {
        this.executor = executor;
    }

    protected ExecutorService createExecutorService() {
        return Executors.newSingleThreadExecutor(new ThreadFactory() {

            public Thread newThread(Runnable r) {
                Thread th = new Thread(r);
                th.setName("jME Terrain Thread");
                th.setDaemon(true);
                return th;
            }
        });
    }

    @Override
    protected void controlUpdate(float tpf) {
        // list of cameras for when terrain supports multiple cameras (ie split screen)
        if (lodCalculator == null)
            return;
        if (!enabled) {
            if (!hasResetLod) {
                // this will get run once
                hasResetLod = true;
                lodCalculator.turnOffLod();
            }
        }
        if (cameras != null) {
            if (cameraLocations.isEmpty() && !cameras.isEmpty()) {
                for (// populate them
                Camera c : // populate them
                cameras) {
                    cameraLocations.add(c.getLocation());
                }
            }
            updateLOD(cameraLocations, lodCalculator);
        }
    }

    /**
     * Call this when you remove the terrain or this control from the scene.
     * It will clear up any threads it had.
     */
    public void detachAndCleanUpControl() {
        if (executor != null)
            executor.shutdownNow();
        getSpatial().removeControl(this);
    }

    // do all of the LOD calculations
    protected void updateLOD(List<Vector3f> locations, LodCalculator lodCalculator) {
        if (getSpatial() == null) {
            return;
        }
        // update any existing ones that need updating
        updateQuadLODs();
        if (lodCalculator.isLodOff()) {
            // we want to calculate the base lod at least once
            if (lodOffCount == 1)
                return;
            else
                lodOffCount++;
        } else
            lodOffCount = 0;
        if (lastCameraLocations != null) {
            if (!forceUpdate && lastCameraLocationsTheSame(locations) && !lodCalculator.isLodOff())
                // don't update if in same spot
                return;
            else
                lastCameraLocations = cloneVectorList(locations);
            forceUpdate = false;
        } else {
            lastCameraLocations = cloneVectorList(locations);
            return;
        }
        if (isLodCalcRunning()) {
            return;
        }
        setLodCalcRunning(true);
        if (executor == null)
            executor = createExecutorService();
        prepareTerrain();
        UpdateLOD updateLodThread = getLodThread(locations, lodCalculator);
        indexer = executor.submit(updateLodThread);
    }

    /**
     * Force the LOD to update instantly, does not wait for the camera to move.
     * It will reset once it has updated.
     */
    public void forceUpdate() {
        this.forceUpdate = true;
    }

    protected void prepareTerrain() {
        TerrainQuad terrain = (TerrainQuad) getSpatial();
        // cache the terrain's world transforms so they can be accessed on the separate thread safely
        terrain.cacheTerrainTransforms();
    }

    protected UpdateLOD getLodThread(List<Vector3f> locations, LodCalculator lodCalculator) {
        return new UpdateLOD(locations, lodCalculator);
    }

    /**
     * Back on the ogl thread: update the terrain patch geometries
     */
    private void updateQuadLODs() {
        if (indexer != null) {
            if (indexer.isDone()) {
                try {
                    HashMap<String, UpdatedTerrainPatch> updated = indexer.get();
                    if (updated != null) {
                        // do the actual geometry update here
                        for (UpdatedTerrainPatch utp : updated.values()) {
                            utp.updateAll();
                        }
                    }
                } catch (InterruptedException ex) {
                    Logger.getLogger(TerrainLodControl.clreplaced.getName()).log(Level.SEVERE, null, ex);
                } catch (ExecutionException ex) {
                    Logger.getLogger(TerrainLodControl.clreplaced.getName()).log(Level.SEVERE, null, ex);
                } finally {
                    indexer = null;
                }
            }
        }
    }

    private boolean lastCameraLocationsTheSame(List<Vector3f> locations) {
        boolean theSame = true;
        for (Vector3f l : locations) {
            for (Vector3f v : lastCameraLocations) {
                if (!v.equals(l)) {
                    theSame = false;
                    return false;
                }
            }
        }
        return theSame;
    }

    protected synchronized boolean isLodCalcRunning() {
        return lodCalcRunning.get();
    }

    protected synchronized void setLodCalcRunning(boolean running) {
        lodCalcRunning.set(running);
    }

    private List<Vector3f> cloneVectorList(List<Vector3f> locations) {
        List<Vector3f> cloned = new ArrayList<Vector3f>();
        for (Vector3f l : locations) cloned.add(l.clone());
        return cloned;
    }

    public Control cloneForSpatial(Spatial spatial) {
        if (spatial instanceof Terrain) {
            List<Camera> cameraClone = new ArrayList<Camera>();
            if (cameras != null) {
                for (Camera c : cameras) {
                    cameraClone.add(c);
                }
            }
            TerrainLodControl cloned = new TerrainLodControl((Terrain) spatial, cameraClone);
            cloned.setLodCalculator(lodCalculator.clone());
            return cloned;
        }
        return null;
    }

    public void setCamera(Camera camera) {
        List<Camera> cams = new ArrayList<Camera>();
        cams.add(camera);
        setCameras(cams);
    }

    public void setCameras(List<Camera> cameras) {
        this.cameras = cameras;
        cameraLocations.clear();
        for (Camera c : cameras) {
            cameraLocations.add(c.getLocation());
        }
    }

    @Override
    public void setSpatial(Spatial spatial) {
        super.setSpatial(spatial);
        if (spatial instanceof Terrain) {
            this.terrain = (Terrain) spatial;
        }
    }

    public void setTerrain(Terrain terrain) {
        this.terrain = terrain;
    }

    public LodCalculator getLodCalculator() {
        return lodCalculator;
    }

    public void setLodCalculator(LodCalculator lodCalculator) {
        this.lodCalculator = lodCalculator;
    }

    @Override
    public void setEnabled(boolean enabled) {
        this.enabled = enabled;
        if (!enabled) {
            // reset the lod levels to max detail for the terrain
            hasResetLod = false;
        } else {
            hasResetLod = true;
            lodCalculator.turnOnLod();
        }
    }

    /**
     * Calculates the LOD of all child terrain patches.
     */
    protected clreplaced UpdateLOD implements Callable<HashMap<String, UpdatedTerrainPatch>> {

        protected List<Vector3f> camLocations;

        protected LodCalculator lodCalculator;

        protected UpdateLOD(List<Vector3f> camLocations, LodCalculator lodCalculator) {
            this.camLocations = camLocations;
            this.lodCalculator = lodCalculator;
        }

        public HashMap<String, UpdatedTerrainPatch> call() throws Exception {
            // long start = System.currentTimeMillis();
            // if (isLodCalcRunning()) {
            // return null;
            // }
            setLodCalcRunning(true);
            TerrainQuad terrainQuad = (TerrainQuad) getSpatial();
            // go through each patch and calculate its LOD based on camera distance
            HashMap<String, UpdatedTerrainPatch> updated = new HashMap<String, UpdatedTerrainPatch>();
            // 'updated' gets populated here
            boolean lodChanged = terrainQuad.calculateLod(camLocations, updated, lodCalculator);
            if (!lodChanged) {
                // not worth updating anything else since no one's LOD changed
                setLodCalcRunning(false);
                return null;
            }
            // then calculate its neighbour LOD values for seaming in the shader
            terrainQuad.findNeighboursLod(updated);
            // 'updated' can get added to here
            terrainQuad.fixEdges(updated);
            terrainQuad.reIndexPages(updated, lodCalculator.usesVariableLod());
            // setUpdateQuadLODs(updated); // set back to main ogl thread
            setLodCalcRunning(false);
            return updated;
        }
    }

    @Override
    public void write(JmeExporter ex) throws IOException {
        super.write(ex);
        OutputCapsule oc = ex.getCapsule(this);
        oc.write((Node) terrain, "terrain", null);
        oc.write(lodCalculator, "lodCalculator", null);
    }

    @Override
    public void read(JmeImporter im) throws IOException {
        super.read(im);
        InputCapsule ic = im.getCapsule(this);
        terrain = (Terrain) ic.readSavable("terrain", null);
        lodCalculator = (LodCalculator) ic.readSavable("lodCalculator", new DistanceLodCalculator());
    }
}

17 Source : TerrainGrid.java
with Apache License 2.0
from neuroph

@Override
public Material getMaterial(Vector3f worldLocation) {
    if (worldLocation == null)
        return null;
    Vector3f tileCell = getTileCell(worldLocation);
    Terrain terrain = cache.get(tileCell);
    if (terrain == null)
        // terrain not loaded for that cell yet!
        return null;
    return terrain.getMaterial(worldLocation);
}

17 Source : TerrainUtils.java
with Apache License 2.0
from neuroph

/**
 * Re-attach the camera to the LOD control.
 * Called when the scene is opened and will only
 * update the control if there is already a terrain present in
 * the scene.
 */
public static void enableLodControl(Camera camera, Node rootNode) {
    Terrain terrain = (Terrain) findTerrain(rootNode);
    if (terrain == null)
        return;
    TerrainLodControl control = ((Spatial) terrain).getControl(TerrainLodControl.clreplaced);
    if (control != null) {
        control.setCamera(camera);
    }
}

17 Source : TerrainUtils.java
with GNU Lesser General Public License v3.0
from huliqing

/**
 * Get the scale of the texture at the specified layer.
 * @param terrain
 * @param layer
 * @return
 */
public final static Float getDiffuseTextureScale(Terrain terrain, int layer) {
    if (terrain == null)
        return 1f;
    MatParam matParam = terrain.getMaterial().getParam("DiffuseMap_" + layer + "_scale");
    if (matParam == null)
        return -1f;
    return (Float) matParam.getValue();
}

17 Source : TerrainUtils.java
with GNU Lesser General Public License v3.0
from huliqing

/**
 * 获取法线贴图,如果不存在则返回null.
 * @param terrain
 * @param layer
 * @return
 */
public final static Texture getNormalTexture(Terrain terrain, int layer) {
    MatParam matParam;
    if (layer == 0)
        matParam = terrain.getMaterial().getParam("NormalMap");
    else
        matParam = terrain.getMaterial().getParam("NormalMap_" + layer);
    if (matParam == null || matParam.getValue() == null) {
        return null;
    }
    Texture tex = (Texture) matParam.getValue();
    return tex;
}

17 Source : TerrainUtils.java
with GNU Lesser General Public License v3.0
from huliqing

public final static Texture doGetAlphaTexture(Terrain terrain, int alphaLayer) {
    if (terrain == null)
        return null;
    MatParam matParam = null;
    if (alphaLayer == 0)
        matParam = terrain.getMaterial().getParam("AlphaMap");
    else if (alphaLayer == 1)
        matParam = terrain.getMaterial().getParam("AlphaMap_1");
    else if (alphaLayer == 2)
        matParam = terrain.getMaterial().getParam("AlphaMap_2");
    if (matParam == null || matParam.getValue() == null) {
        return null;
    }
    Texture tex = (Texture) matParam.getValue();
    return tex;
}

17 Source : TerrainUtils.java
with GNU Lesser General Public License v3.0
from huliqing

public final static Texture getDiffuseTexture(Terrain terrain, int layer) {
    if (terrain == null)
        return null;
    MatParam matParam;
    if (layer == 0)
        matParam = terrain.getMaterial().getParam("DiffuseMap");
    else
        matParam = terrain.getMaterial().getParam("DiffuseMap_" + layer);
    if (matParam == null || matParam.getValue() == null) {
        return null;
    }
    Texture tex = (Texture) matParam.getValue();
    return tex;
}

17 Source : SimpleModelEntityControlTile.java
with GNU Lesser General Public License v3.0
from huliqing

@Override
public void updateState() {
    super.updateState();
    // 当选择的是地形的时候,,注意:地形在载入的时候需要重新设置材质,使用地形中的所有分块指定同一个材质实例,
    // 否则指定刷到特定的材质上。
    if (target.getSpatial() instanceof Terrain) {
        Terrain terrain = (Terrain) target.getSpatial();
        target.getSpatial().setMaterial(terrain.getMaterial());
    }
}

17 Source : PaintTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

private Texture getAlphaTexture(Terrain terrain, int alphaLayer) {
    if (terrain == null)
        return null;
    MatParam matParam = null;
    if (alphaLayer == 0)
        matParam = terrain.getMaterial(null).getParam("AlphaMap");
    else if (alphaLayer == 1)
        matParam = terrain.getMaterial(null).getParam("AlphaMap_1");
    else if (alphaLayer == 2)
        matParam = terrain.getMaterial(null).getParam("AlphaMap_2");
    if (matParam == null || matParam.getValue() == null) {
        return null;
    }
    Texture tex = (Texture) matParam.getValue();
    return tex;
}

16 Source : TextureLayerSettings.java
with Apache License 2.0
from JavaSaBr

/**
 * Get a texture scale of the level.
 *
 * @param layer the layer.
 * @return the texture scale or -1.
 */
@FromAnyThread
public float getTextureScale(final int layer) {
    final Function<Integer, String> layerToScaleName = getLayerToScaleName();
    if (layerToScaleName == null) {
        return -1F;
    }
    final Terrain terrain = getTerrain();
    final Material material = terrain.getMaterial();
    final MatParam matParam = material.getParam(layerToScaleName.apply(layer));
    return matParam == null ? -1F : (float) matParam.getValue();
}

16 Source : TerrainUtils.java
with GNU Lesser General Public License v3.0
from huliqing

/**
 * 设置法线贴图
 * @param terrain
 * @param layer
 * @param texture
 */
public final static void setNormalTexture(Terrain terrain, int layer, Texture texture) {
    texture.setWrap(Texture.WrapMode.Repeat);
    if (layer == 0) {
        terrain.getMaterial().setTexture("NormalMap", texture);
    } else {
        terrain.getMaterial().setTexture("NormalMap_" + layer, texture);
    }
}

16 Source : TerrainUtils.java
with GNU Lesser General Public License v3.0
from huliqing

public final static void setDiffuseTexture(Terrain terrain, int layer, Texture texture) {
    texture.setWrap(Texture.WrapMode.Repeat);
    if (layer == 0)
        terrain.getMaterial().setTexture("DiffuseMap", texture);
    else
        terrain.getMaterial().setTexture("DiffuseMap_" + layer, texture);
}

16 Source : TexLayerTool.java
with GNU Lesser General Public License v3.0
from huliqing

public void setTextureScale(int layer, float scale) {
    if (layer >= TerrainUtils.MAX_TEXTURES)
        return;
    Terrain terrain = getTerrain();
    if (terrain == null)
        return;
    TerrainUtils.setDiffuseTextureScale(terrain, layer, scale);
    setModified(true);
    texLayerListener.forEach(t -> {
        t.onLayerChanged(this);
    });
}

16 Source : TexLayerTool.java
with GNU Lesser General Public License v3.0
from huliqing

/**
 * 设置指定图层的贴图,如果texturePath为null则移除这个贴图
 * @param layer
 * @param texturePath
 */
public void setDiffuseTexture(int layer, String texturePath) {
    if (layer >= TerrainUtils.MAX_TEXTURES)
        return;
    Terrain terrain = getTerrain();
    if (terrain == null)
        return;
    if (texturePath == null) {
        TerrainUtils.removeDiffuseTexture(terrain, layer);
    } else {
        Texture tex = editor.getreplacedetManager().loadTexture(texturePath);
        TerrainUtils.setDiffuseTexture(terrain, layer, tex);
    }
    setModified(true);
    texLayerListener.forEach(t -> {
        t.onLayerChanged(this);
    });
}

16 Source : SlopeTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

// remove20170314, 这个方法在JME3.1.0-stable-FINAL的时候有BUG,具体表现在计算desiredHeight的时候错误,比期望的高出很多。
// private void modifyHeight(Terrain terrain, Vector3f point1, Vector3f point2, Vector3f current, float radius, float weight, boolean precise, boolean lock) {
// // Make sure we go for the right direction, or we could be creating a slope to the oposite side
// if (point1.y > point2.y) {
// Vector3f temp = point1;
// point1 = point2;
// point2 = temp;
// }
// 
// Vector3f subtract = point2.subtract(point1);
// 
// int radiusStepsX = (int) (radius / ((Node) terrain).getLocalScale().x);
// int radiusStepsZ = (int) (radius / ((Node) terrain).getLocalScale().z);
// 
// float xStepAmount = ((Node) terrain).getLocalScale().x;
// float zStepAmount = ((Node) terrain).getLocalScale().z;
// 
// List<Vector2f> locs = new ArrayList<Vector2f>();
// List<Float> heights = new ArrayList<Float>();
// undoHeights = new ArrayList<Float>();
// 
// Plane p1 = new Plane();
// Plane p2 = new Plane();
// p1.setOriginNormal(point1, point1.subtract(point2).normalize());
// p2.setOriginNormal(point2, point1.subtract(point2).normalize());
// 
// for (int z = -radiusStepsZ; z < radiusStepsZ; z++)
// for (int x = -radiusStepsX; x < radiusStepsX; x++) {
// 
// float locX = current.x + (x * xStepAmount);
// float locZ = current.z + (z * zStepAmount);
// 
// if (ToolUtils.isInRadius(locX - current.x, locZ - current.z, radius)) { // see if it is in the radius of the tool
// Vector2f terrainLoc = new Vector2f(locX, locZ);
// 
// // adjust height based on radius of the tool
// float terrainHeightAtLoc = terrain.getHeightmapHeight(terrainLoc) * ((Node) terrain).getWorldScale().y;
// float distance = point1.distance(new Vector3f(locX, terrainHeightAtLoc, locZ).subtractLocal(point1).project(subtract).addLocal(point1));
// float desiredHeight = point1.y + (point2.y - point1.y) * distance;
// if (!lock || (lock && p1.whichSide(new Vector3f(locX, 0f, locZ)) != p2.whichSide(new Vector3f(locX, 0f, locZ)))) {
// if (!precise) {
// float epsilon = 0.1f * weight; // rounding error for snapping
// 
// float adj = 0;
// if (terrainHeightAtLoc < desiredHeight)
// adj = 1;
// else if (terrainHeightAtLoc > desiredHeight)
// adj = -1;
// 
// adj *= weight;
// 
// adj *= ToolUtils.calculateRadiusPercent(radius, locX - current.x, locZ - current.z);
// 
// // test if adjusting too far and then cap it
// if (adj > 0 && ToolUtils.floatGreaterThan((terrainHeightAtLoc + adj), desiredHeight, epsilon))
// adj = desiredHeight - terrainHeightAtLoc;
// else
// if (adj < 0 && ToolUtils.floatLessThan((terrainHeightAtLoc + adj), desiredHeight, epsilon))
// adj = terrainHeightAtLoc - desiredHeight;
// 
// if (!ToolUtils.floatEquals(adj, 0, 0.001f)) {
// locs.add(terrainLoc);
// heights.add(adj);
// }
// } else {
// locs.add(terrainLoc);
// heights.add(desiredHeight / ((Node) terrain).getLocalScale().y);
// undoHeights.add(terrainHeightAtLoc / ((Node) terrain).getLocalScale().y);
// }
// }
// }
// }
// undoLocs = locs;
// if (!precise)
// undoHeights = heights;
// 
// // do the actual height adjustment
// if (precise)
// terrain.setHeight(locs, heights);
// else
// terrain.adjustHeight(locs, heights);
// 
// ((Node) terrain).updateModelBound(); // or else we won't collide with it where we just edited
// }
private void resetHeight(Terrain terrain, List<Vector2f> undoLocs, List<Float> undoHeights, boolean precise) {
    if (precise)
        terrain.setHeight(undoLocs, undoHeights);
    else {
        List<Float> neg = new ArrayList<Float>();
        for (Float f : undoHeights) {
            neg.add(f * -1f);
        }
        terrain.adjustHeight(undoLocs, neg);
    }
    ((Node) terrain).updateModelBound();
}

16 Source : SlopeTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

@Override
public void redo() {
    // 消除地形的位置和旋转导致的偏移,但是不消除缩放,这们允许地形在缩放、旋转和移动后进行编辑。
    // 否则地形不能旋转和移动
    Terrain terrain = getTerrain(selectObj);
    Spatial terrainSpaitla = (Spatial) terrain;
    Vector3f truePoint1 = point1.subtract(terrainSpaitla.getWorldTranslation());
    terrainSpaitla.getWorldRotation().inverse().mult(truePoint1, truePoint1);
    Vector3f truePoint2 = point2.subtract(terrainSpaitla.getWorldTranslation());
    terrainSpaitla.getWorldRotation().inverse().mult(truePoint2, truePoint2);
    Vector3f trueCurrent = current.subtract(terrainSpaitla.getWorldTranslation());
    terrainSpaitla.getWorldRotation().inverse().mult(trueCurrent, trueCurrent);
    modifyHeight(terrain, truePoint1, truePoint2, trueCurrent, radius, weight, precise, lock);
}

16 Source : LevelTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

private void resetHeight(Terrain terrain, List<Vector2f> undoLocs, List<Float> undoHeights, boolean precision) {
    if (precision)
        terrain.setHeight(undoLocs, undoHeights);
    else {
        List<Float> neg = new ArrayList<Float>();
        for (Float f : undoHeights) {
            neg.add(f * -1f);
        }
        terrain.adjustHeight(undoLocs, neg);
    }
    ((Node) terrain).updateModelBound();
}

15 Source : TextureLayerSettings.java
with Apache License 2.0
from JavaSaBr

/**
 * Get a diffuse normal of the level.
 *
 * @param layer the layer.
 * @return the normal texture or null.
 */
@FromAnyThread
@Nullable
public Texture getNormal(final int layer) {
    final Function<Integer, String> layerToNormalName = getLayerToNormalName();
    if (layerToNormalName == null) {
        return null;
    }
    final Terrain terrain = getTerrain();
    final Material material = terrain.getMaterial();
    final MatParam matParam = material.getParam(layerToNormalName.apply(layer));
    if (matParam == null || matParam.getValue() == null) {
        return null;
    }
    return (Texture) matParam.getValue();
}

15 Source : TextureLayerSettings.java
with Apache License 2.0
from JavaSaBr

/**
 * Get a diffuse texture of the level.
 *
 * @param layer the layer.
 * @return the diffuse texture or null.
 */
@FromAnyThread
@Nullable
public Texture getDiffuse(final int layer) {
    final Function<Integer, String> layerToDiffuseName = getLayerToDiffuseName();
    if (layerToDiffuseName == null) {
        return null;
    }
    final Terrain terrain = getTerrain();
    final Material material = terrain.getMaterial();
    final MatParam matParam = material.getParam(layerToDiffuseName.apply(layer));
    if (matParam == null || matParam.getValue() == null) {
        return null;
    }
    return (Texture) matParam.getValue();
}

15 Source : TextureLayerSettings.java
with Apache License 2.0
from JavaSaBr

/**
 * Get a alpha texture of the level.
 *
 * @param layer the layer.
 * @return the alpha texture or null.
 */
@FromAnyThread
@Nullable
public Texture getAlpha(final int layer) {
    final Function<Integer, String> layerToAlphaName = getLayerToAlphaName();
    if (layerToAlphaName == null) {
        return null;
    }
    final Terrain terrain = getTerrain();
    final Material material = terrain.getMaterial();
    final MatParam matParam = material.getParam(layerToAlphaName.apply(layer));
    if (matParam == null || matParam.getValue() == null) {
        return null;
    }
    return (Texture) matParam.getValue();
}

15 Source : PaintTerrainToolControl.java
with Apache License 2.0
from JavaSaBr

@JmeThread
@NotNull
private Vector2f getPointPercentagePosition(@NotNull final Terrain terrain, @NotNull final Vector3f localPoint, @NotNull final Vector3f localScale, @NotNull final Vector2f result) {
    result.set(localPoint.x, -localPoint.z);
    float scale = localScale.getX();
    // already centered on Terrain's node origin (0,0)
    float scaledSize = terrain.getTerrainSize() * scale;
    // shift the bottom left corner up to 0,0
    result.addLocal(scaledSize / 2, scaledSize / 2);
    // get the location as a percentage
    result.divideLocal(scaledSize);
    return result;
}

15 Source : TexLayerTool.java
with GNU Lesser General Public License v3.0
from huliqing

/**
 * 移除一个贴图图层
 * @param layer
 */
public void removeTextureLayer(int layer) {
    if (layer >= TerrainUtils.MAX_TEXTURES)
        return;
    Terrain terrain = getTerrain();
    if (terrain == null)
        return;
    TerrainUtils.removeDiffuseTexture(terrain, layer);
    TerrainUtils.removeNormalTexture(terrain, layer);
    TerrainUtils.doClearAlphaMap(terrain, layer);
    setModified(true);
    setModifiedAlpha(true);
    texLayerListener.forEach(t -> {
        t.onLayerChanged(this);
    });
}

15 Source : PaintTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

private Vector2f getPointPercentagePosition(Terrain terrain, Vector3f worldLoc) {
    Vector2f uv = new Vector2f(worldLoc.x, -worldLoc.z);
    float scale = ((Node) terrain).getWorldScale().x;
    // already centered on Terrain's node origin (0,0)
    // uv.subtractLocal(((Node)terrain).getWorldTranslation().x*scale, ((Node)terrain).getWorldTranslation().z*scale); // center it on 0,0
    float scaledSize = terrain.getTerrainSize() * scale;
    // shift the bottom left corner up to 0,0
    uv.addLocal(scaledSize / 2, scaledSize / 2);
    // get the location as a percentage
    uv.divideLocal(scaledSize);
    return uv;
}

14 Source : TexLayerTool.java
with GNU Lesser General Public License v3.0
from huliqing

/**
 * 设置指定图层的法线贴图,如果texturePath为null则移除这个贴图
 * @param layer
 * @param texturePath
 */
public void setNormalTexture(int layer, String texturePath) {
    if (layer >= TerrainUtils.MAX_TEXTURES)
        return;
    Terrain terrain = getTerrain();
    if (terrain == null)
        return;
    if (texturePath == null) {
        TerrainUtils.removeNormalTexture(terrain, layer);
    } else {
        Texture tex = editor.getreplacedetManager().loadTexture(texturePath);
        TerrainUtils.setNormalTexture(terrain, layer, tex);
    }
    setModified(true);
    texLayerListener.forEach(t -> {
        t.onLayerChanged(this);
    });
}

14 Source : PaintTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

public void paintTexture(Terrain terrain, Vector3f markerLocation, float toolRadius, float toolWeight, int selectedTextureIndex) {
    if (selectedTextureIndex < 0 || markerLocation == null)
        return;
    // 4 = rgba = 4 textures
    int alphaIdx = selectedTextureIndex / 4;
    Texture tex = getAlphaTexture(terrain, alphaIdx);
    Image image = tex.getImage();
    Vector2f UV = getPointPercentagePosition(terrain, markerLocation);
    // get the radius of the brush in pixel-percent
    float brushSize = toolRadius / (terrain.getTerrainSize() * ((Node) terrain).getWorldScale().x);
    // selectedTextureIndex/4 is an int floor, do not simplify the equation
    int texIndex = selectedTextureIndex - ((selectedTextureIndex / 4) * 4);
    boolean erase = toolWeight < 0;
    if (erase)
        toolWeight *= -1;
    doPaintAction(texIndex, image, UV, true, brushSize, erase, toolWeight);
    tex.getImage().setUpdateNeeded();
}

13 Source : TextureLayerSettings.java
with Apache License 2.0
from JavaSaBr

/**
 * Set a new texture scale to a level.
 *
 * @param scale the texture scale.
 * @param layer the layer.
 */
@FromAnyThread
public void setTextureScale(final float scale, final int layer) {
    final Function<Integer, String> layerToScaleName = getLayerToScaleName();
    if (layerToScaleName == null) {
        return;
    }
    final Terrain terrain = getTerrain();
    final Material material = terrain.getMaterial();
    final String paramName = layerToScaleName.apply(layer);
    final MatParam matParam = material.getParam(paramName);
    final Float current = matParam == null ? null : (Float) matParam.getValue();
    final PropertyOperation<ChangeConsumer, Node, Float> operation = new PropertyOperation<>(getTerrainNode(), TERRAIN_PARAM, scale, current);
    operation.setApplyHandler((node, newScale) -> {
        NodeUtils.visitGeometry(getTerrainNode(), geometry -> {
            final Material geometryMaterial = geometry.getMaterial();
            final MatParam param = geometryMaterial.getParam(paramName);
            if (param == null && (newScale == null || newScale == -1F)) {
                return;
            }
            if (newScale == null || newScale == -1F) {
                geometryMaterial.clearParam(paramName);
            } else {
                geometryMaterial.setFloat(paramName, newScale);
            }
        });
    });
    final ModelChangeConsumer changeConsumer = paintingComponent.getChangeConsumer();
    changeConsumer.execute(operation);
}

13 Source : TexLayerTool.java
with GNU Lesser General Public License v3.0
from huliqing

/**
 * 添加一个贴图图层
 * @param layer
 */
public void addTextureLayer(int layer) {
    if (layer >= TerrainUtils.MAX_TEXTURES)
        return;
    Terrain terrain = getTerrain();
    if (terrain == null)
        return;
    TerrainUtils.setDiffuseTextureScale(terrain, layer, TerrainUtils.DEFAULT_TEXTURE_SCALE);
    Texture tex = editor.getreplacedetManager().loadTexture(TerrainUtils.TERRAIN_DIRT);
    TerrainUtils.setDiffuseTexture(terrain, layer, tex);
    setModified(true);
    texLayerListener.forEach(t -> {
        t.onLayerChanged(this);
    });
}

13 Source : TexLayerTool.java
with GNU Lesser General Public License v3.0
from huliqing

/**
 * 获取图层,如果当前没有选择中地形物体,则该方法可能返回null.
 * @return
 */
public List<TexLayer> getLayers() {
    Terrain terrain = getTerrain();
    if (terrain == null)
        return null;
    List<TexLayer> layers = new ArrayList(TerrainUtils.MAX_TEXTURES);
    Texture normalTex;
    for (int i = 0; i < TerrainUtils.MAX_TEXTURES; i++) {
        Texture tex = TerrainUtils.getDiffuseTexture(terrain, i);
        if (tex == null) {
            break;
        }
        TexLayer layer = new TexLayer();
        layer.setDiffuseMap(tex.getName());
        layer.setScale(TerrainUtils.getDiffuseTextureScale(terrain, i));
        normalTex = TerrainUtils.getNormalTexture(terrain, i);
        if (normalTex != null) {
            layer.setNormalMap(normalTex.getName());
        }
        layers.add(layer);
    }
    return layers;
}

13 Source : PaintTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

@Override
public void undo() {
    // 消除地形的位置和旋转导致的偏移,但是不消除缩放,这们允许地形在缩放、旋转和移动后进行编辑。
    // 否则地形不能旋转和移动
    Terrain terrain = getTerrain(selectObj);
    Spatial terrainSpaitla = (Spatial) terrain;
    Vector3f trueLocation = worldLoc.subtract(terrainSpaitla.getWorldTranslation());
    terrainSpaitla.getWorldRotation().inverse().mult(trueLocation, trueLocation);
    paintTexture(terrain, trueLocation, radius, -weight, selectedTextureIndex);
}

13 Source : PaintTerrainToolAction.java
with GNU Lesser General Public License v3.0
from huliqing

@Override
public void redo() {
    Terrain terrain = getTerrain(selectObj);
    Spatial terrainSpaitla = (Spatial) terrain;
    Vector3f trueLocation = worldLoc.subtract(terrainSpaitla.getWorldTranslation());
    terrainSpaitla.getWorldRotation().inverse().mult(trueLocation, trueLocation);
    paintTexture(terrain, trueLocation, radius, weight, selectedTextureIndex);
}

12 Source : TextureLayerSettings.java
with Apache License 2.0
from JavaSaBr

/**
 * Set a new normal texture to a level.
 *
 * @param texture the normal texture.
 * @param layer   the layer.
 */
@FromAnyThread
public void setNormal(@Nullable final Texture texture, final int layer) {
    final Function<Integer, String> layerToNormalName = getLayerToNormalName();
    if (layerToNormalName == null) {
        return;
    }
    final Terrain terrain = getTerrain();
    final Material material = terrain.getMaterial();
    final String paramName = layerToNormalName.apply(layer);
    final MatParam matParam = material.getParam(paramName);
    final Texture current = matParam == null ? null : (Texture) matParam.getValue();
    if (texture != null) {
        texture.setWrap(Texture.WrapMode.Repeat);
    }
    final PropertyOperation<ChangeConsumer, Node, Texture> operation = new PropertyOperation<>(getTerrainNode(), TERRAIN_PARAM, texture, current);
    operation.setApplyHandler((node, newTexture) -> NodeUtils.visitGeometry(node, geometry -> updateTexture(newTexture, paramName, geometry)));
    final ModelChangeConsumer changeConsumer = paintingComponent.getChangeConsumer();
    changeConsumer.execute(operation);
}

12 Source : TextureLayerSettings.java
with Apache License 2.0
from JavaSaBr

/**
 * Set a new diffuse texture to a level.
 *
 * @param texture the new texture.
 * @param layer   the layer.
 */
@FromAnyThread
public void setDiffuse(@Nullable final Texture texture, final int layer) {
    final Function<Integer, String> layerToDiffuseName = getLayerToDiffuseName();
    if (layerToDiffuseName == null) {
        return;
    }
    final Terrain terrain = getTerrain();
    final Material material = terrain.getMaterial();
    final String paramName = layerToDiffuseName.apply(layer);
    final MatParam matParam = material.getParam(paramName);
    final Texture current = matParam == null ? null : (Texture) matParam.getValue();
    if (texture != null) {
        texture.setWrap(Texture.WrapMode.Repeat);
    }
    final PropertyOperation<ChangeConsumer, Node, Texture> operation = new PropertyOperation<>(getTerrainNode(), TERRAIN_PARAM, texture, current);
    operation.setApplyHandler((node, newTexture) -> NodeUtils.visitGeometry(node, geometry -> updateTexture(newTexture, paramName, geometry)));
    final ModelChangeConsumer changeConsumer = paintingComponent.getChangeConsumer();
    changeConsumer.execute(operation);
}

12 Source : TerrainUtils.java
with GNU Lesser General Public License v3.0
from huliqing

public final static void doClearAlphaMap(Terrain terrain, int selectedTextureIndex) {
    // 4 = rgba = 4 textures
    int alphaIdx = selectedTextureIndex / 4;
    // selectedTextureIndex/4 is an int floor
    int texIndex = selectedTextureIndex - ((selectedTextureIndex / 4) * 4);
    // selectedTextureIndex - (alphaIdx * 4)
    Texture tex = doGetAlphaTexture(terrain, alphaIdx);
    Image image = tex.getImage();
    PaintTerrainToolAction paint = new PaintTerrainToolAction();
    ColorRGBA color = ColorRGBA.Black;
    for (int y = 0; y < image.getHeight(); y++) {
        for (int x = 0; x < image.getWidth(); x++) {
            // gets the color at that location (false means don't write to the buffer)
            paint.manipulatePixel(image, x, y, color, false);
            switch(texIndex) {
                case 0:
                    color.r = 0;
                    break;
                case 1:
                    color.g = 0;
                    break;
                case 2:
                    color.b = 0;
                    break;
                case 3:
                    color.a = 0;
                    break;
            }
            color.clamp();
            // set the new color
            paint.manipulatePixel(image, x, y, color, true);
        }
    }
    image.getData(0).rewind();
    tex.getImage().setUpdateNeeded();
}

See More Examples