Draw a dashed line

I thought to draw a line with dash or dot style is easy but it isn’t. Unfortunately, I can’t use the jme Line class due to select the object by mouse. The Line class isn’t collidable therefore I draw my lines as follow:

	public class MyLine extends Mesh {
	private float[] position = null;
	private float tolerance;
	public MyLine(float[] position) {
		this.position = position;
		int[] indexes = new int[(2 * (position.length / 3)) - 2];
		for (int i = 0, j = 0; i < indexes.length; i += 2, j++) {
			indexes[i] = j;
			indexes[i + 1] = j + 1;
		}
		setBuffer(VertexBuffer.Type.Position, 3, position);
		setBuffer(VertexBuffer.Type.Index, 2, indexes);
		setMode(Mode.Lines);
		updateBound();
	}
}

How can I draw this line as dashed or dotted line?

That’s not really collidable either. How does one define the intersection between one thing with no width (a ray) and another thing with no width (a line).

…if it’s working at all then it’s not working correctly.

If you want selectable ‘lines’ then you may need to implement it yourself… or if performance isn’t a concern (like their aren’t many lines) then use some invisible cylinders around the lines.

…but as for making a dashed line… give it a dashed texture.

The class MyLine implements all necessary method to pick the line and it works. But my problem is: How can I draw the line as dashed line.

I didn’t add all methods to the class, I just wanted to show how I draw my line.
Do you have maybe an example how to add a texture to create a dashed line? I have really no idea.

All you need is a texture with some solid areas and some transparent areas. The transparency will give you the dash effect.

this is a quick example I made using line mesh and unlit material:
UPDATED

import com.jme3.app.SimpleApplication;
import com.jme3.material.Material;
import com.jme3.math.ColorRGBA;
import com.jme3.math.Vector2f;
import com.jme3.math.Vector3f;
import com.jme3.scene.Geometry;
import com.jme3.scene.Mesh;
import com.jme3.scene.VertexBuffer;
import com.jme3.shader.VarType;
import com.jme3.texture.Texture;
import com.jme3.util.BufferUtils;


public class DashedLineTest extends SimpleApplication {

    public static void main(String[] args) {
        DashedLineTest app = new DashedLineTest();
        app.start();
    }
    
    
    @Override
    public void simpleInitApp() {
        // lighten the Background to help with contrast
        viewPort.setBackgroundColor(ColorRGBA.DarkGray);
        flyCam.setMoveSpeed(15f);
        setupMesh();
    }
    
    private void setupMesh() {
        Mesh mesh = new Mesh();
        mesh.setMode(Mesh.Mode.Lines);
        
        // create an array for the points of the line
        Vector3f[] vertices = new Vector3f[2];
        vertices[0] = new Vector3f(0f, 0f, 0f);
        vertices[1] = new Vector3f(4f, 0f, 0f);
        
        // set the UV for the endpoint to the distance between origin and 
        // endpoint of the line to maintain scale of dashing when used with 
        // Texture.WrapMode.Repeat below, which will repeat the texture in 
        // unit length distances across the full length of the line
        float distance = vertices[1].subtract(vertices[0]).length();
        
        Vector2f[] texCoords = new Vector2f[2];
        texCoords[0] = new Vector2f(0f, 0f);
        texCoords[1] = new Vector2f(distance, 0f);

        mesh.setBuffer(VertexBuffer.Type.Position, 3, BufferUtils.createFloatBuffer(vertices));
        mesh.setBuffer(VertexBuffer.Type.TexCoord, 2, BufferUtils.createFloatBuffer(texCoords));
        mesh.updateBound();
        
        // Transparent texture is required (png with alpha channel) 
        Material unlitMaterial = new Material(assetManager,"Common/MatDefs/Misc/Unshaded.j3md");
        Texture texture = assetManager.loadTexture("Textures/DashedLine_128x8.png");
        texture.setWrap(Texture.WrapMode.Repeat);
        unlitMaterial.setTexture("ColorMap", texture);
        unlitMaterial.getAdditionalRenderState().setBlendMode(RenderState.BlendMode.Alpha);
        //unlitMaterial.setParam("AlphaDiscardThreshold", VarType.Float, 0.9f);
        unlitMaterial.getAdditionalRenderState().setLineWidth(2f);
        
        Geometry geom = new Geometry("Dashed Line Geometry", mesh);
        geom.setMaterial(unlitMaterial);
        
        rootNode.attachChild(geom);
    }
        
}

I am not 100% certain how the Unshaded Material Parameter “AlphaDiscardThreshold” is used properly, but I thought this was required to get my custom png to remove the alpha channel, as it turns out, I had forgotten to set the Material blendMode to Alpha.

image used can be found here:
Imgur

You may need it anyway but there was no alpha blending because the blend mode was never set to alpha blending.

1 Like

Thanks @pspeed, I knew I was overlooking something. Snippet has been updated.

Probably you want it in the transparent bucket also.

Usual settings for something with alpha:
-blend mode to an alpha mode (required)
-bucket to transparent (probably required)
-alphaDiscardThreshold (as needed if you have alpha z blending issues)

2 Likes

Did you ever draw the dashed line you wanted?