Punkte verschieben und löschen

Dies ist eine Fortsetztung des Threads
http://forum.byte-welt.net/java-forum-das-java-welt-kompetenz-zentrum-wir-wissen-und-helfen-/spiele-und-multimedia-programmierung/17181-komischer-bug-beim-obj-laden-2.html#post122982
Das Thema hat sich etwas gewandelt, also mache ich einen neuen auf. Die problematik kann in Post 38 des vorherigen Threads nachgesehen werden. Also:

Ich hab es jetzt mal wie folgt verändert, das sollte das Problem mit den Indexen lösen, tut’s aber nicht.

for(int z = 0; z < inds.length; z++){
				int gelöschterPunkt = inds[z];
				for(int i = 0; i < coords.size(); i++){
					if(i==gelöschterPunkt){
						coords.remove(i);
						i--;
						if(inds[z] < coords.size()-1){
							for(int a = 0; a < inds.length; a++){
								inds[a]--;
							}
						}
					}
				}
			}

Nur überflogen, selbst mit Link recht kontextfrei, und (wie üblich grausligst benannte Variablennamen) wenn “inds” für irgendwelche Indizes steht, muss man davon ausgehen, dass die NUR um 1 verringert werden sollen, wenn sie vorher GRÖSSER waren, als der index, der gelöscht wurde.

Ich werde mal ein KSKB zusammenstellen.

So, hier das KSKB.
Ich habe jeden Punkt doppelt gemacht, um zu testen, ob das mit der Problematik aus dem alten Thread auch funktioniert. Außerdem updatet sich das Mesh nicht, wenn man einen Punkt löscht und es flimmert(Ich weiß nicht woran diese Dinge liegen). Aber aus dem Konsolenoutput sollte relativ schnell klar werden worin das Problem besteht: es wird zuviel gelöscht.

import static org.lwjgl.opengl.GL15.*;
import static org.lwjgl.opengl.GL11.*;

import java.nio.FloatBuffer;
import java.nio.IntBuffer;
import java.util.ArrayList;

import org.lwjgl.BufferUtils;
import org.lwjgl.LWJGLException;
import org.lwjgl.input.Mouse;
import org.lwjgl.opengl.ContextAttribs;
import org.lwjgl.opengl.Display;
import org.lwjgl.opengl.DisplayMode;
import org.lwjgl.opengl.GL15;
import org.lwjgl.opengl.PixelFormat;
import org.lwjgl.util.glu.GLU;
import org.lwjgl.util.vector.Vector3f;


public class KSKB {

	float[] coords = {
			-1, -1, -1,
			-1, -1, -1,
			
			 1, -1, -1,
			 1, -1, -1,
			 
			-1,  1, -1,
			-1,  1, -1,
			
			 1,  1, -1,
			 1,  1, -1,
			 
			 
			-1, -1,  1,
			-1, -1,  1,
				
			 1, -1,  1,
			 1, -1,  1,
				 
			-1,  1,  1,
			-1,  1,  1,
				
			 1,  1,  1,
			 1,  1,  1
	};
	int[] indexe = {
			0, 2, 4, 5, 3, 7,
			8, 10, 12, 13, 11, 15,
			0, 2, 8, 9, 3, 11,
			0, 4, 8, 9, 5, 13,
			2, 6, 10, 11, 7, 15,
			4, 6, 12, 13, 7, 15
	};
	private FloatBuffer vertexBuffer;
	private int vboID;
	private IntBuffer indexBuffer;
	private FloatBuffer modelMatrix = BufferUtils.createFloatBuffer(16);
	private FloatBuffer projectionMatrix = BufferUtils.createFloatBuffer(16);
	private IntBuffer viewport = BufferUtils.createIntBuffer(16);
	private int geklickterPunkt;
	private boolean punktLöschen;
	
	public KSKB(){
		final int GL_MAJOR_VERSION = 1;
        final int GL_MINOR_VERSION = 0;
        
        final DisplayMode displayMode = new DisplayMode(854, 480);
        final PixelFormat pixelFormat = new PixelFormat();
        final ContextAttribs contextAttribs = new ContextAttribs(GL_MAJOR_VERSION, GL_MINOR_VERSION);
        
        try {
			Display.setDisplayMode(displayMode);
			Display.create(pixelFormat, contextAttribs);
		} catch (LWJGLException e) {
			e.printStackTrace();
		}
        Display.setLocation(760, 210);
        Display.setTitle("KSKB");
        Display.setResizable(true);
        init(coords, indexe);
        projectionMatrix = BufferUtils.createFloatBuffer(16);
        projectionMatrix.put(projection(45, Display.getWidth()/Display.getHeight(), 0.1f, 100));
        projectionMatrix.flip();
        while(!Display.isCloseRequested()){
        	zeugMitMaus();
        	glViewport(0, 0, Display.getWidth(), Display.getHeight());
        	glGetInteger(GL_VIEWPORT, viewport);
        	glClear(GL_DEPTH_BUFFER_BIT);
        	glMatrixMode(GL_PROJECTION);
        	GLU.gluPerspective(45, Display.getWidth()/Display.getHeight(), 0.1f, 100);
        	glMatrixMode(GL_MODELVIEW);
        	glTranslatef(0, 0, -5);
        	glRotatef(45, 1, 0, 0);
        	glGetFloat(GL_MODELVIEW_MATRIX, modelMatrix);
        	glColor4f(1, 1, 1, 1);
        	glEnableClientState(GL_VERTEX_ARRAY);
        	glBindBuffer(GL_ARRAY_BUFFER, vboID);
        	glVertexPointer(3, GL_FLOAT, 0, 0);
        	
        	glDrawElements(GL_TRIANGLES, indexBuffer);
        	glColor4f(1, 0, 0, 1);
        	glPointSize(5f);
        	glClear(GL_DEPTH_BUFFER_BIT);
        	for(int i = 0; i < coords.length/3; i++){
        		glDrawArrays(GL_POINTS, i, 1);
        	}
        	
        	glDisableClientState(GL_VERTEX_ARRAY);
        	Display.update();
        }
	}
	
	public static float[] projection(final float fovy, final float aspect, final float zNear, final float zFar) {
		 
        final double f = (1.0 / Math.tan(Math.toRadians(fovy / 2.0)));
 
        final float[] m = new float[16];
 
        m[0] = (float) (f / aspect);
        m[5] = (float) (f);
        m[10] = (zFar + zNear) / (zNear - zFar);
        m[11] = (-1);
        m[14] = (2 * zFar * zNear) / (zNear - zFar);
        m[15] = 0;
 
        return m;
    }
	
	private void zeugMitMaus() {
		if(Mouse.isButtonDown(0)){
			for(int i = 0; i < coords.length; i+=3){
				FloatBuffer punktPos = BufferUtils.createFloatBuffer(3);
				GLU.gluProject(coords**, coords[i+1], coords[i+2], modelMatrix, projectionMatrix, viewport, punktPos);
				if(punktPos.get(0) > Mouse.getX()-10 && punktPos.get(0) < Mouse.getX()+10 && 
						punktPos.get(1) > Display.getHeight()-Mouse.getY()-10 && punktPos.get(1) < Display.getHeight()-Mouse.getY()+10){
					geklickterPunkt = i/3;
					punktLöschen = true;
					break;
				}else{
					punktLöschen = false;
				}
			}
		}
		if(punktLöschen){
			punktLöschen(geklickterPunkt);
			init(coords, indexe);
			punktLöschen = false;
		}
	}

	private void init(float[] coords, int[] indexe) {
		vertexBuffer = BufferUtils.createFloatBuffer(coords.length);
		vertexBuffer.put(coords);
		vertexBuffer.flip();
		vboID = createVBO(vertexBuffer, vboID);
		indexBuffer = BufferUtils.createIntBuffer(indexe.length);
		indexBuffer.put(indexe);
		indexBuffer.flip();
	}

	public static void main(String[] args){
		new KSKB();
	}

	private int[] getGleichePunkte(int punktIndex) {
		ArrayList<Integer> indexe = new ArrayList<Integer>();
		Vector3f vergleich = new Vector3f(vertexBuffer.get(punktIndex), vertexBuffer.get(punktIndex+1), vertexBuffer.get(punktIndex+2));
		for(int i = 0; i < vertexBuffer.capacity(); i+=3){
			Vector3f vec = new Vector3f(vertexBuffer.get(i), vertexBuffer.get(i+1), vertexBuffer.get(i+2));
			if(vec.x == vergleich.x && vec.y == vergleich.y && vec.z == vergleich.z){
				indexe.add(i);
			}
		}
		int[] inds = new int[indexe.size()];
		for(int i = 0; i < inds.length; i++){
			inds** = indexe.get(i);
		}
		return inds;
	}
	
	public void punktLöschen(int punktIndex) {
		int[] inds = getGleichePunkte(punktIndex);
		System.out.println("Folgender Punkt wurde geklickt: "+punktIndex);
		System.out.println("Der Punkt kommt "+inds.length+" Mal vor");
		System.out.println("Vorher:");
		ArrayList<Float[]> coords = new ArrayList<Float[]>();
		for(int i = 0; i < this.coords.length; i+=3){
			coords.add(new Float[]{this.coords**, this.coords[i+1], this.coords[i+2]});
			System.out.println(this.coords**+" "+this.coords[i+1]+" "+this.coords[i+2]);
		}
		for(int z = 0; z < inds.length; z++){
			int gelöschterPunkt = inds[z];
			for(int i = 0; i < coords.size(); i++){
				if(i==gelöschterPunkt){
					coords.remove(i);
					i--;
					if(inds[z] < coords.size()-1){
						for(int a = 0; a < inds.length; a++){
							inds[a]--;
						}
					}
				}
			}
		}
		int a = 0;
		System.out.println("Nachher:");
		this.coords = new float[coords.size()*3];
		for(int i = 0; i < coords.size(); i+=3){
			this.coords** = coords.get(a)[0];
			this.coords[i+1] = coords.get(a)[1];
			this.coords[i+2] = coords.get(a)[2];
			System.out.println(this.coords**+" "+this.coords[i+1]+" "+this.coords[i+2]);
			a++;
		}
	}

	private int createVBO(FloatBuffer b, int id) {
		GL15.glDeleteBuffers(id);
		id = glGenBuffers();
        glBindBuffer(GL_ARRAY_BUFFER, id);
        glBufferData(GL_ARRAY_BUFFER, b, GL_STATIC_DRAW);
        glBindBuffer(GL_ARRAY_BUFFER, 0);
		return id;
	}
}

warum musst du denn daraus schon wieder unbenutzbaren lwjgl-Quatsch machen?

eine Liste mit float-Arrays, manuell definieren 242.434, 5434.34, usw.,
eine Liste mit Indexen, Schleifen darüber,
das kann in ein echtes Testprogramm, main-Methode, kopieren, laufen lassen, fertig zum Fehler,
jeder könnte es in Minuten korrigieren

wenn du kompliziere Testwerte hast, dann könntest du sie aus deinem Original-Programmlauf kopieren,
etwas Arbeit, gewiss, aber das ist der Preis dafür wenn im Forum allgemein gefragt

so fraglich ob sich wer mit lwjgl findet, vielleicht genauso schnell, vielleicht weitere Monate zu warten,

            int gelöschterPunkt = inds[z];
            for(int i = 0; i < coords.size(); i++){
                if(i==gelöschterPunkt){
                    coords.remove(i);
                    i--;

wie schon im anderen Thread gesagt, schön für Helfer wenn du Tipps unkommentiert ignorierst…,
ist eine innere Schleife über coords unsinnig,
entweder remove mit dem aktuellen Index gelöschterPunkt ausführen oder nicht, entscheide dich

wenn überhaupt so ein unsinniges Konstrukt, dann ist i-- drin besonders fatal,
damit wird i beim nächsten Schleifenschritt wieder erhöht und ist wieder == gelöschterPunkt, alles weitere in der Liste wird gelöscht…

wie ein einfaches überall ausführbares Testprogramm sofort zeigt:


	public static void main(String[] args) throws Exception {
		List<String> list = new ArrayList<String>();
		list.add("A");
		list.add("B");
		list.add("C");
		list.add("D");

		int gelöschterPunkt = 1;
		for (int i = 0; i < list.size(); i++) {
			System.out.println("nächster Schleifendurchlauf, i= " + i);
			if (i == gelöschterPunkt) {
				System.out.println("lösche nun Element "+list.get(i));
				list.remove(i);
				i--;
			}
		}
        // korrekt statt dieser ganzen unsinnigen Schleife bei einem Index dagegen: 
        // list.remove(gelöschterPunkt);
 
		System.out.println(list);
	}
}```
Ausgabe:

nächster Schleifendurchlauf, i= 0
nächster Schleifendurchlauf, i= 1
lösche nun Element B
nächster Schleifendurchlauf, i= 1
lösche nun Element C
nächster Schleifendurchlauf, i= 1
lösche nun Element D
[A]


System.out.println() bei jedem Schritt deines Programms kannst du dir im Zweifel um Richtigkeit auch angewöhnen, 
so siehst du dann vielleicht endlich, was passiert

Also, der Code ist keineswegs unausführbar, da sich das hier um ein Problem innerhalb eines LWJGL basierten Programms sollte der Code einwandfrei laufen, sofern man LWJGL installiert hat, dauert keine 5 Minuten und macht viel Freude.
Ich dachte, es freut alle, wenn es schön übersichtlich und schön grafisch gestaltet ist(Was ja nicht ganz so gut gelang :)), aber meinetwegen, hier eine Fassung, die nur Konsolenoutput gibt. Ich habe deinen Code angepasst, da nicht nur ein Buchstabe sondern ein Punkt, also 3 Einträge gelöscht werden sollen.Die Umwandlung von Array zu List und andersherum habe ich gelassen, da es einfacher ist, am Anfang das Zeug in einen Array einzutragen. Den Array mit den Indexen habe ich auch gelassen, da der nächste Schritt sein wird, die Dreiecke zu den gelöschten Punkten auch zu löschen. Ich hoffe, dieser Code macht dir mehr Freude:

import java.util.ArrayList;
import java.util.Scanner;

public class KSKB {

	float[] coords = {
			-1, -1, -1,
			-1, -1, -1,
			
			 1, -1, -1,
			 1, -1, -1,
			 
			-1,  1, -1,
			-1,  1, -1,
			
			 1,  1, -1,
			 1,  1, -1,
			 
			 
			-1, -1,  1,
			-1, -1,  1,
				
			 1, -1,  1,
			 1, -1,  1,
				 
			-1,  1,  1,
			-1,  1,  1,
				
			 1,  1,  1,
			 1,  1,  1
	};
	int[] indexe = {
			0, 2, 4, 5, 3, 7,
			8, 10, 12, 13, 11, 15,
			0, 2, 8, 9, 3, 11,
			0, 4, 8, 9, 5, 13,
			2, 6, 10, 11, 7, 15,
			4, 6, 12, 13, 7, 15
	};
	private int geklickterPunkt;
	private boolean punktLöschen;
	private boolean exit = false;
	private Scanner s;
	
	public KSKB(){
		s = new Scanner(System.in);
        while(!exit){
        	zeugMitMaus();
        }
	}
	
	public static float[] projection(final float fovy, final float aspect, final float zNear, final float zFar) {
		 
        final double f = (1.0 / Math.tan(Math.toRadians(fovy / 2.0)));
 
        final float[] m = new float[16];
 
        m[0] = (float) (f / aspect);
        m[5] = (float) (f);
        m[10] = (zFar + zNear) / (zNear - zFar);
        m[11] = (-1);
        m[14] = (2 * zFar * zNear) / (zNear - zFar);
        m[15] = 0;
 
        return m;
    }
	
	private void zeugMitMaus() {
		int punkt = s.nextInt();
		if(punkt < coords.length/3){
			geklickterPunkt = punkt;
			punktLöschen = true;
		}else{
			punktLöschen = false;
		}
		if(punktLöschen){
			punktLöschen(geklickterPunkt);
			punktLöschen = false;
		}
	}
	
	public static void main(String[] args){
		new KSKB();
	}

	private int[] getGleichePunkte(int punktIndex) {
		ArrayList<Integer> indexe = new ArrayList<Integer>();
		float[] vergleich = new float[]{coords[punktIndex], coords[punktIndex+1], coords[punktIndex+2]};
		for(int i = 0; i < coords.length; i+=3){
			float[] vec = new float[]{coords**, coords[i+1], coords[i+2]};
			if(vec[0] == vergleich[0] && vec[1] == vergleich[1] && vec[2] == vergleich[2]){
				indexe.add(i);
			}
		}
		int[] inds = new int[indexe.size()];
		for(int i = 0; i < inds.length; i++){
			inds** = indexe.get(i);
		}
		return inds;
	}
	
	public void punktLöschen(int punktIndex) {
		int[] inds = getGleichePunkte(punktIndex);
		System.out.println("Folgender Punkt wurde geklickt: "+punktIndex);
		System.out.println("Der Punkt kommt "+inds.length+" Mal vor");
		ArrayList<Float> coords = new ArrayList<Float>();
		for(int i = 0; i < this.coords.length; i++){
			coords.add(this.coords**);
		}
		System.out.println("Vorher:");
		for(int i = 0; i < coords.size(); i+=3){
			System.out.println(coords.get(i)+" "+coords.get(i+1)+" "+coords.get(i+2));
		}
		for(int z = 0; z < inds.length; z++){
			int gelöschterPunkt = inds[z];
			int a = 0;
	        for (int i = 0; i < coords.size(); i+=3) {
	            System.out.println("nächster Schleifendurchlauf, i= " + i);
	            if (a == gelöschterPunkt) {
	                System.out.println("lösche nun Element "+coords.get(i)+" "+coords.get(i+1)+" "+coords.get(i+2));
	                coords.remove(i);
	                coords.remove(i);
	                coords.remove(i);
	            }
	            a++;
	        }
		}
		System.out.println("Nachher:");
		this.coords = new float[coords.size()];
		for(int i = 0; i < coords.size(); i++){
			this.coords** = coords.get(i);
		}
		for(int i = 0; i < this.coords.length; i+=3){
			System.out.println(this.coords**+" "+this.coords[i+1]+" "+this.coords[i+2]);
		}
	}
}

die Bedienung, dass man eine Zahl eingeben muss und was das dann bedeutet, darf man sich selber heraussuchen?
weitere Regel: Testprogramme besser nie mit Eingaben, Wiederholung des Problems in Schleifen usw. kompliziert machen,

einfach punkt = 2 in der hier unpassend benannten Methode zeugMitMaus() und Schleife weg und die Rechnung liefe einmal sauber (oder eben noch falsch) durch

wenn kompliziertes wie das über 7 Zeilen definierte Array indexe oder die 15 Zeilen Methode projection() nicht mehr mitspielt, dann auch ruhig löschen…


neu hast du nun also a in der Schleife, von eine Schleife über coords bist du wohl nicht abzubekommen?
na, da du eh nie was dazu erklärend oder an Fragen schreibst, muss ich wohl auch nichts mehr dazu sagen

eine korrekte Taktik ist, wie ich schon im anderen Thema geschrieben hatte, in Reihenfolge rückwärts zu löschen, dann keine Komplikationen

			int gelöschterPunkt = inds[z];
			coords.remove(gelöschterPunkt + 2); // Reihenfolge der drei Befehle wichtig
			coords.remove(gelöschterPunkt + 1);
			coords.remove(gelöschterPunkt);
		}

Oh, sorry. Ich hatte vergessen projection zu löschen und die “unpassend benannte” Methode heißt auch nurnoch so, weil sie früher etwas mit der Maus drin hatte. Natürlich hätte ich noch angeben sollen, was man eingeben kann: Den Punkt den Man löschen will, also eine Zahl von 0 bis 16. Und das Array Indexe spielt wie gesagt im nächsten Schritt eine Rolle, denn sobald die Koordinaten richtig gelöscht werden, müssen auch die zugehörigen Indexe gelöscht werden.Dank deiner Hilfe ist dieser 2. Schritt nun erreicht:
Ich weiß nicht, inwieweit du dich mit der Materie der Indexe für Punkte auskennst, aber man kann den Indexarray in 3er Gruppen einteilen. Jede 3er Gruppe repräsentiert ein Dreieck. Und wenn ein Punkt gelöscht wird, müssen alle Dreiecke, in denen der Index des gelöschten Punktes vorkommt gelöscht werden. Und der Rest der Indexe angepasst werden, da sich ja die Punkte verändern. Aber bei diesem Entwurf wird irgendwie gar nichts gelöscht.

import java.util.ArrayList;

public class KSKB {

	float[] coords = {
			-1, -1, -1,
			-1, -1, -1,
			
			 1, -1, -1,
			 1, -1, -1,
			 
			-1,  1, -1,
			-1,  1, -1,
			
			 1,  1, -1,
			 1,  1, -1,
			 
			 
			-1, -1,  1,
			-1, -1,  1,
				
			 1, -1,  1,
			 1, -1,  1,
				 
			-1,  1,  1,
			-1,  1,  1,
				
			 1,  1,  1,
			 1,  1,  1
	};
	int[] indexe = {
			0, 2, 4, 5, 3, 7,
			8, 10, 12, 13, 11, 15,
			0, 2, 8, 9, 3, 11,
			0, 4, 8, 9, 5, 13,
			2, 6, 10, 11, 7, 15,
			4, 6, 12, 13, 7, 15
	};
	private int geklickterPunkt;
	private boolean punktLöschen;
	
	public KSKB(){
		int punkt = 0;
		if(punkt < coords.length/3){
			geklickterPunkt = punkt;
			punktLöschen = true;
		}else{
			punktLöschen = false;
		}
		if(punktLöschen){
			punktLöschen(geklickterPunkt);
			punktLöschen = false;
		}
	}
	
	public static void main(String[] args){
		new KSKB();
	}

	private int[] getGleichePunkte(int punktIndex) {
		ArrayList<Integer> indexe = new ArrayList<Integer>();
		float[] vergleich = new float[]{coords[punktIndex], coords[punktIndex+1], coords[punktIndex+2]};
		for(int i = 0; i < coords.length; i+=3){
			float[] vec = new float[]{coords**, coords[i+1], coords[i+2]};
			if(vec[0] == vergleich[0] && vec[1] == vergleich[1] && vec[2] == vergleich[2]){
				indexe.add(i);
			}
		}
		int[] inds = new int[indexe.size()];
		for(int i = 0; i < inds.length; i++){
			inds** = indexe.get(i);
		}
		return inds;
	}
	
	public void punktLöschen(int punktIndex) {
		int[] inds = getGleichePunkte(punktIndex);
		System.out.println("Folgender Punkt wurde geklickt: "+punktIndex);
		System.out.println("Der Punkt kommt "+inds.length+" Mal vor");
		ArrayList<Float> coords = new ArrayList<Float>();
		ArrayList<Integer[]> dreiecke = new ArrayList<Integer[]>();
		for(int i = 0; i < this.coords.length; i++){
			coords.add(this.coords**);
		}
		for(int i = 0; i < this.indexe.length; i+=3){
			dreiecke.add(new Integer[]{this.indexe**, this.indexe[i+1], this.indexe[i+2]});
		}
		System.out.println("Vorher:");
		for(int i = 0; i < dreiecke.size(); i++){
			System.out.println(dreiecke.get(i)[0]+" "+dreiecke.get(i)[1]+" "+dreiecke.get(i)[2]);
		}
		for (int z = inds.length - 1; z >= 0; z--) {
            int gelöschterPunkt = inds[z];
            coords.remove(gelöschterPunkt + 2);
            coords.remove(gelöschterPunkt + 1);
            coords.remove(gelöschterPunkt);
            
            for(int i = dreiecke.size()-1; i >= 0; i--){
    			if(gelöschterPunkt == dreiecke.get(i)[0] || gelöschterPunkt == dreiecke.get(i)[1] || gelöschterPunkt == dreiecke.get(i)[2]){
    				dreiecke.remove(i);
    			}
    		}
            for(int i = 0; i < dreiecke.size(); i++){
            	for(int a = 0; a < dreiecke.get(i).length; a++){
            		if(dreiecke.get(i)[a] > gelöschterPunkt){
            			dreiecke.get(i)[a]--;
            		}
            	}
            }
        }
		System.out.println("Nachher:");
		this.coords = new float[coords.size()];
		for(int i = 0; i < coords.size(); i++){
			this.coords** = coords.get(i);
		}
		for(int i = 0; i < this.indexe.length; i+=3){
			System.out.println(this.indexe**+" "+this.indexe[i+1]+" "+this.indexe[i+2]);
		}
	}
}

wie war es noch mit System.out.println() nun zu einem neuen Problem?
meine Güte, mit der Technik hast du es ja wirklich schwer, etwas zu schaffen,
ich programmiere gewiss genauso viele Fehler, aber ich schaue sie jedesmal nach, sofort alles zu finden

dreiecke wird übrigens durchaus verkleinert, von 12 auf 7 Elemente runter,
am Ende gibst du aber das nicht berührte Index-Array aus…

immerhin dreiecke rückwärts durchgegangen, ein Lichtblick :wink:
Senken der Punkt-Werte in dreieck könnte auch hinkommen, da 'gelöschterPunkt’e rückwärts runter geht

Ja, ich habe mir etwas von deinen Lehren gemerkt.
Was merkwürdig ist, ist 1. die Indexe, nach der Prozedur rauskommen und 2., dass die beiden gleichen Punkte 0 und 3 sind, obwohl es ja eigentlich 0 und 1 sein müssten.

import java.util.ArrayList;

public class KSKB {

	float[] coords = {
			-1, -1, -1,
			-1, -1, -1,
			
			 1, -1, -1,
			 1, -1, -1,
			 
			-1,  1, -1,
			-1,  1, -1,
			
			 1,  1, -1,
			 1,  1, -1,
			 
			 
			-1, -1,  1,
			-1, -1,  1,
				
			 1, -1,  1,
			 1, -1,  1,
				 
			-1,  1,  1,
			-1,  1,  1,
				
			 1,  1,  1,
			 1,  1,  1
	};
	int[] indexe = {
			1, 2, 4, 5, 3, 7,
			8, 10, 12, 13, 11, 15,
			0, 2, 8, 9, 3, 11,
			0, 4, 8, 9, 5, 13,
			2, 6, 10, 11, 7, 15,
			4, 6, 12, 13, 7, 15
	};
	private int geklickterPunkt;
	private boolean punktLöschen;
	
	public KSKB(){
		int punkt = 0;
		if(punkt < coords.length/3){
			geklickterPunkt = punkt;
			punktLöschen = true;
		}else{
			punktLöschen = false;
		}
		if(punktLöschen){
			punktLöschen(geklickterPunkt);
			punktLöschen = false;
		}
	}
	
	public static void main(String[] args){
		new KSKB();
	}

	private int[] getGleichePunkte(int punktIndex) {
		ArrayList<Integer> indexe = new ArrayList<Integer>();
		float[] vergleich = new float[]{coords[punktIndex], coords[punktIndex+1], coords[punktIndex+2]};
		for(int i = 0; i < coords.length; i+=3){
			float[] vec = new float[]{coords**, coords[i+1], coords[i+2]};
			if(vec[0] == vergleich[0] && vec[1] == vergleich[1] && vec[2] == vergleich[2]){
				indexe.add(i);
			}
		}
		int[] inds = new int[indexe.size()];
		for(int i = 0; i < inds.length; i++){
			inds** = indexe.get(i);
		}
		return inds;
	}
	
	public void punktLöschen(int punktIndex) {
		int[] inds = getGleichePunkte(punktIndex);
		System.out.println("Folgender Punkt wurde geklickt: "+punktIndex);
		System.out.println("Der Punkt kommt "+inds.length+" Mal vor , nämlich "+inds[0]+" & "+inds[1]);
		ArrayList<Float> coords = new ArrayList<Float>();
		ArrayList<Integer[]> dreiecke = new ArrayList<Integer[]>();
		for(int i = 0; i < this.coords.length; i++){
			coords.add(this.coords**);
		}
		for(int i = 0; i < this.indexe.length; i+=3){
			dreiecke.add(new Integer[]{this.indexe**, this.indexe[i+1], this.indexe[i+2]});
		}
		System.out.println("Vorher:");
		for(int i = 0; i < dreiecke.size(); i++){
			System.out.println(dreiecke.get(i)[0]+" "+dreiecke.get(i)[1]+" "+dreiecke.get(i)[2]);
		}
		for (int z = inds.length - 1; z >= 0; z--) {
            int gelöschterPunkt = inds[z];
            coords.remove(gelöschterPunkt + 2);
            coords.remove(gelöschterPunkt + 1);
            coords.remove(gelöschterPunkt);
            
            for(int i = dreiecke.size()-1; i >= 0; i--){
            	System.out.println("Prüfe Dreieck "+i+" für Punkt "+gelöschterPunkt);
    			if(gelöschterPunkt == dreiecke.get(i)[0] || gelöschterPunkt == dreiecke.get(i)[1] || gelöschterPunkt == dreiecke.get(i)[2]){
    				System.out.println("Index kommt drin vor, lösche");
    				dreiecke.remove(i);
    			}
    		}
            for(int i = 0; i < dreiecke.size(); i++){
            	for(int a = 0; a < dreiecke.get(i).length; a++){
            		System.out.println("Prüfe Index "+a+" von Dreieck "+i);
            		if(dreiecke.get(i)[a] > gelöschterPunkt){
            			System.out.println("Index ist größer, verkleinern");
            			dreiecke.get(i)[a]--;
            		}
            	}
            }
        }
		System.out.println("Nachher:");
		this.indexe = new int[dreiecke.size()*3];
		for(int i = 0; i < dreiecke.size(); i+=3){
			this.indexe**   = dreiecke.get(i/3)[0];
			this.indexe[i+1] = dreiecke.get(i/3)[1];
			this.indexe[i+2] = dreiecke.get(i/3)[2];
		}
		for(int i = 0; i < this.indexe.length; i+=3){
			System.out.println(this.indexe**+" "+this.indexe[i+1]+" "+this.indexe[i+2]);
		}
	}
}

ich werde dir nicht ewig helfen, anderseits ging es ja bisher jahrelange auch ohne meine Beteiligung, also nicht allzu viel Gefahr,
aber vielleicht doch mehr selber versuchen und nur bei wirklich harten Nüssen nachfragen?

die coords-Liste ist durchgängig mit je drei Indexen, wie kannst gerade du das nicht wissen/ bedenken?
Punkt 0 steht für 0, 1 und 2,
Punkt 3 steht für 3, 4 und 5
deswegen ja auch

            coords.remove(gelöschterPunkt + 1);
            coords.remove(gelöschterPunkt);

dreiecke.get(i)[a] > gelöschterPunkt dürfte aber in der Tat im Moment nicht passen, da wieder auf 3 = 1 zurückzurechnen,
oder lieber objektorientierte vorgehen bzw. zumindest coords als eine Liste oder Array von 3er-Arrays wie auch schon ‘dreiecke’,
wäre dann auch gleich einheitlicher

kann man auch direkt definieren:

            {-1, -1, -1},
            {-1, -1, -1},

usw.

  1. for(int i = 0; i < dreiecke.size(); i+=3){
    hier gehört ein System.out.println() rein, welche i werden alle abgearbeitet, was macht jeder Schleifendurchlauf,
    wieviel wird das indexe-Array befüllt,
    dann kommt der Fehler ganz von alleine heraus, es ist nur zu arbeiten

[ot]

[QUOTE=SlaterB]oder lieber objektorientierte vorgehen bzw. zumindest coords als eine Liste oder Array von 3er-Arrays wie auch schon ‘dreiecke’,
wäre dann auch gleich einheitlicher
[/QUOTE]
Sämtliche bisherigen Versuche meinerseits, ihn zu etwas “sauberer”, “systematischer”, “strukturierterer” Entwicklung zu bewegen, schlugen fehl. Anscheinend haben manche Leute eine viel höhere Frustrationstoleranz als ich. Ich jedenfalls find’ den Code grauslig.
[/ot]

Ja, natürlich, wie konnte ich das vergessen, 3 = 1. Dann muss es natürlich so aussehen:

for(int i = dreiecke.size()-1; i >= 0; i--){
            	System.out.println("Prüfe Dreieck "+i+" für Punkt "+gelöschterPunkt);
    			if(gelöschterPunkt/3 == dreiecke.get(i)[0] || gelöschterPunkt/3 == dreiecke.get(i)[1] || gelöschterPunkt/3 == dreiecke.get(i)[2]){
    				System.out.println("Index kommt drin vor, lösche");
    				dreiecke.remove(i);
    			}
    		}
            for(int i = 0; i < dreiecke.size(); i++){
            	for(int a = 0; a < dreiecke.get(i).length; a++){
            		System.out.println("Prüfe Index "+a+" von Dreieck "+i);
            		if(dreiecke.get(i)[a] > gelöschterPunkt/3){
            			System.out.println("Index ist größer, verkleinern");
            			dreiecke.get(i)[a]--;
            		}
            	}
            }
 @Marco13  Ich hab keine Ahnung, was hier schon wieder auszusetzen ist. Der Code ist doch ordentlich und, wenn er funktioniert funktionell. ;)

Außerdem Verstehe ich nicht, warum danach so viele 0en sind, ich hab mal den höchsten Index genommen, der geht(damit nichts verringert wird), aber trotzdem kommen da 0en vor, ich lösche doch nur Einträge aus der Liste, und setzte keinen Index auf 0.

Dass du offenbar wirklich versuchen willst, eine Art “Mesh-Editor” zu basteln, ohne Klassen für Vertices und Dreiecke zu haben, ist, gestelzt-positiv formuliert, “ambitioniert”.

Geh’ doch mal schrittweise zurück, wo das Problem herkommt: Irgendwelche Indizes stimmen nicht. Warum? Weil du eine Liste bräuchtest, aber einen Array verwendest, und versuchst, Listen-Funktionalitäten (wie z.B. das Löschen und “Nachrücken” der übrigen Elemente) händisch nachzubauen - aber nicht etwa systematisch, im Sinne von eigenen Methoden, die diese Funktionen übernehmen, sondern jeweils dort, wo du gerade irgendwas machen willst, mit einer üblen, gärenden Mischung aus int[]-Arrays, Integer[]-Arrays, und Listen von beiden. Warum ““musst”” du das alles machen? Pff, keine Ahnung, irgendwas mit OBJ-Dateien, wo du etwas rausliest und das dann irgendwie ändern willst, weil irgendwas doppelt vorkommt, wie auch immer.

Ich hatte schonmal gesagt: Es gibt ein Problem, an dem auch schon schlauere Leute als du und ich sich die Zähne ausgebissen haben. Und dieses Problem ist: Meshes so repräsentieren, dass man sie leicht rendern UND leicht editieren kann. Zum Rendern müssen sie als rohe Arrays vorliegen (genaugenommen als Buffer auf der GPU, bzw. Direct Buffers auf Java-Seite). Zum Editieren braucht man schöne objektorientierte Strukturen. Das passt einfach nicht zusammen. Man kann nur versuchen, den Kompromiß zu finden, der (im Hinblick auf die selbst gesetzten Prioritäten) am wenigsten Kacke ist. Wenn du dir deinen aktuellen Code ansiehst, wirst du merken, dass du einen “Kompromiß” gefunden hast, der einerseits die klarste Trennung zwischen beiden Seiten ist: Du kopierst erst alles aus den Arrays in “Strukturen”, veränderst die dann, und erstellst aus diesen “Strukturen” wieder Arrays. Andererseits sind diese “Strukturen” eben sowas wie “ArrayList<Integer[]>” sind, und NICHT etwa etwas, womit man vernünftig arbeiten kann. Es gibt 1001 Möglichkeiten, wie man das ganze selbst MIT dieser (in bezug auf die Performance ggf. fragwürdigen) Konvertierung bei jeder Änderung schreiben könnte. Jetzt sowas suggestives zu schreiben wie

class TriangleMeshData {
    float vertices[];
    int indices[];
}
class Mesh {
    // Dem geneigten Leser zur Übung überlassen
}

TriangleMeshData deleteVertex(TriangleMeshData t, int index)
{
    Mesh mesh = convertToMesh(t);
    mesh.removeVertex(index);
    return convertToTriangleMeshData(mesh);
}

würde wohl nichts bringen, … nichts ist so einfach wie es aussieht. Aber dass du nicht selbst denkst, dass so eine Zeile wie

if(gelöschterPunkt/3 == dreiecke.get(i)[0] || gelöschterPunkt/3 == dreiecke.get(i)[1] || gelöschterPunkt/3 == dreiecke.get(i)[2]){ .. }

“schöner” wäre, wenn dort

if (triangles.get(i).contains(deletedVertex)) { ... }

stünde, wundert mich etwas. Du müßtest dich doch eigentlich schon lange genug über dieses Index-Gefrickel geärgert haben.

das war deine Frage 1. und das habe ich unter 1. auch beantwortet, mal nicht als komplette Lösung aber als hilfreiche Tipps

Ach, du meintest, dass das mit den 0en von der Konvertierung von Liste zu Array wieder kommt? Ja, das schau ich mir nochmal an.
Diese Liste mit Arrays als Inhalt finde ich insofern praktisch, da in jeder Array ein Dreieck repräsentiert, also 3 Einträge hat, die dann geordnet in der Liste sind. Vielleicht stehe ich da mit der Meinung alleine da, aber ich finde Code ist wesentlich schwerer zu durchschauen und unübersichtlicher, wenn man für jeden noch so kleinen Schritt eine eigene Klasse mit 5 Zeilen Inhalt und 2 Minimethoden macht(überspitzt dargestellt). Also das ist jetzt nicht böse gemeint, oder so.

OK, endlich geschafft, danke für eure Hilfe!

public void punktLöschen(int punktIndex) {
		int[] inds = getGleichePunkte(punktIndex);
		System.out.println("Folgender Punkt wurde geklickt: "+punktIndex/3);
		System.out.println("Der Punkt kommt "+inds.length+" Mal vor , nämlich "+inds[0]/3+" & "+inds[1]/3);
		ArrayList<Float> coords = new ArrayList<Float>();
		ArrayList<Integer[]> dreiecke = new ArrayList<Integer[]>();
		for(int i = 0; i < this.coords.length; i++){
			coords.add(this.coords**);
		}
		for(int i = 0; i < this.indexe.length; i+=3){
			dreiecke.add(new Integer[]{this.indexe**, this.indexe[i+1], this.indexe[i+2]});
		}
		System.out.println("Vorher:");
		for(int i = 0; i < dreiecke.size(); i++){
			System.out.println(dreiecke.get(i)[0]+" "+dreiecke.get(i)[1]+" "+dreiecke.get(i)[2]);
		}
		for (int z = inds.length - 1; z >= 0; z--) {
            int gelöschterPunkt = inds[z];
            coords.remove(gelöschterPunkt + 2);
            coords.remove(gelöschterPunkt + 1);
            coords.remove(gelöschterPunkt);
            
            for(int i = dreiecke.size()-1; i >= 0; i--){
    			if(gelöschterPunkt/3 == dreiecke.get(i)[0] || gelöschterPunkt/3 == dreiecke.get(i)[1] || gelöschterPunkt/3 == dreiecke.get(i)[2]){
    				dreiecke.remove(i);
    			}
    		}
            for(int i = 0; i < dreiecke.size(); i++){
            	for(int a = 0; a < dreiecke.get(i).length; a++){
            		if(dreiecke.get(i)[a] > gelöschterPunkt/3){
            			dreiecke.get(i)[a]--;
            		}
            	}
            }
        }
		System.out.println("Nachher:");
		this.indexe = new int[dreiecke.size()*3];
		for(int i = 0; i < this.indexe.length; i+=3){
			this.indexe**   = dreiecke.get(i/3)[0];
			this.indexe[i+1] = dreiecke.get(i/3)[1];
			this.indexe[i+2] = dreiecke.get(i/3)[2];
		}
		for(int i = 0; i < this.indexe.length; i+=3){
			System.out.println(this.indexe**+" "+this.indexe[i+1]+" "+this.indexe[i+2]);
		}
	}