Daten aus String löschen



  • das problem dabei ist, dass die objekte mit koordinaten gesetzt werden und nicht einfach text ausgegeben wird.
    Mein Fehler ich habe vergessen zu erwähnen das Opengl ebenfalls im Spiel ist.
    Ich poste mal meinen Code, der für das anzeigen verantwortlich ist.

    void COutput::draw(vector2df kh)
    {
            //Das Grundobjekt für die Ausgabe
    	glPushMatrix();
    	glLoadIdentity();
    	glTranslatef(pos.X,pos.Y,0);
    	//glColor3f(0.4,0.4,0.4);
    	glBegin(GL_QUADS);
    		glVertex2f(0,0);
    		glVertex2f(0,size.Y);
    		glVertex2f(size.X,size.Y);
    		glVertex2f(size.X,0);
    	glEnd();
    	glPopMatrix();
    
            // Die aktuelle Zeile
    	GLuint curLine = 1;
            // Die Höhe und die Breite der einzelnen Objekte
    	vector2df charSize(size.X/chars, size.Y/lines);
    
    	glPushMatrix();
    
            // Hier werden erstmal die Position angegeben, an der gezeichnet werden    soll
    	glTranslatef(0,kh.Y+charSize.Y*(lines-1), 0 );
    
            // Hier wird der String durchlaufen und alle Zeichen ausgegeben
    	for(GLuint x=0; x<keyOut.size(); x++) 
    	{
                    //Wenn eine Reihe voll ist, sprich 40 Zeichen, dann mache automatisch einen Umbruch
    		if(x == chars*curLine)
    		{
    			curLine++;
    			glTranslatef(-size.X,-charSize.Y,0);
    		}	
                    // Wenn ein Umbruch eingefügt werden soll
    		if (keyOut[x] == '\n')
    		{
                            //Damit nicht bei jedem Schleifendurchlauf alle Umbrüche gezeichnet werden, mache darauf ein Leerzeichen
    			keyOut[x] = '_';
    
                            // Teste wie viele Zeichen in der Reihe sind und berechne den Rest der noch bis zum Ende gebraucht wird und fürge dafür Leerzeichen ein
                            for(int a=keyOut.size(); a<(chars*curLine); a++)
    			{
    				keyOut += '_';
    			}
    		}
    
                    // Für diese Zeichen soll keine Textur geladen werden
    		if(keyOut[x] == '_' || keyOut[x] == '\n' || keyOut[x] == '>' || keyOut[x] == '<')
    		{
    		}
    		else
    		{
    			(*texChar[keyOut[x]]).bind();
    		}
    
                    // Zeichne die Taste
    		glBegin(GL_QUADS);
    			glTexCoord2f(0,1); glVertex2f(0,0);
    			glTexCoord2f(0,0); glVertex2f(0,charSize.Y);
    			glTexCoord2f(1,0); glVertex2f(charSize.X,charSize.Y);
    			glTexCoord2f(1,1); glVertex2f(charSize.X,0);
    		glEnd();
    
                    // Die Textur wieder ausbinden
    		if(keyOut[x] != '_')
    		{
    			(*texChar[keyOut[x]]).unbind();
    		}
    		glTranslatef(charSize.X,0,0);
    	}
    	glPopMatrix();
    }
    
    bool COutput::add(char Key)
    {
            // Wenn die Esc-Taste gedrückt, lasse die Tastatur verschwinden, sodass nut der Text angezeigt wird.
    	if(Key == '|')
    	{
    		return false;
    	}
            // Wenn die Shift-Taste gedrückt wird
    	if(Key == '>')
    	{
    		if(tall)
    		{
    			std::cout<<"Die Shift-Taste ist gedrückt \n";
    			tall = false;
    		}
    		else
    		{
    			std::cout<<"Die Shift-Taste ist nicht mehr gedrückt \n";
    			tall = true;
    		}
    	}
    
            // Hier wird die letzte Taste gelöscht
    	if(Key == '<' && keyOut.length()>0)
    	{
    		keyOut = keyOut.substr(0,keyOut.length()-1);
    	}
    	else if(keyOut.length() < chars*lines)
    	{
                    // Hier wird je nach groß und Kleinschreibung das Zeichen hinzugefügt
    		if(tall)
    		{
    			Key = toupper(Key);
    			keyOut += Key;
    		}
    		else
    		{
    			Key = tolower(Key);
    			keyOut += Key;
    		}
    	}
    
    	return true;
    }
    

    Das ist mein Code und jetzt möchte ich halt, wenn er beim löschen den Absatz erreicht alle Leerzeichen bis zu zu einem anderen Zeichen löschen, damit man nicht wie bisher alle Leerzeichen einzel löschen muss



  • also das habe ich bis jetzt. Bei diesem Code, tauscht er doch jetzt diese beiden Zeichen (_) mit "" aus oder? Was bewirkt sie zwei?

    keyOut.replace(keyOut.find("__"),2,"");
    

    zweite Frage:
    Wie kann ich in dem gesamten String diese ersetzen? Weil er bei mir das bis jetzt nur einmal macht.

    Ich möchte halt das er erstmal nach hinten die normalen löscht und dann mit einem Schlag alle löscht. Außerdem brauche ich eine noch eine Abfrage, die testet ob noch welche vorhanden sind.
    Also ka wie die if-Abfrage funktioniert.

    Danke



  • wenn du die leerzeichen die du selbst in deinen string reingemacht hast nicht haben willst, dann tu sie doch erst gar nicht rein.



  • das Problem ist, dass er den string füllen MUSS um einen umbruch zu machen. Ich habe jetzt 1000000 Sachen probiert und nichts hat gefuntz bist auf diese Variante.
    Deswegen frag ich hier wie man das so machen kann, weil das reinlogisch klappen müsste.



  • int position = keyOut.find("_"); 
    while (position != string::npos) 
    {
        keyOut.replace(position, 1, "");
        position = keyOut.find( " ", position + 1 );
    }
    

    so also an sich sollte er doch jetzt die schleife solange durchlaufen bis er das zeichen nicht mehr findet oder? Weil irgendwie klappt das nicht. der macht das immer nur einmal



  • wie waer' denn sowas?

    if(keyOut[x] == '\n')
    {
      glTranslatef(-summeDerCharsDieserZeile, ZeilenAbstand, 0); 
    }
    


  • das war meine erste Variante

    if (keyOut[x] == '\n')
        {
    	int y = 0;
    	y = (chars*curLine)-keyOut.size();
    	glTranslatef(-(y*charSize.X),-charSize.Y,0);
        }
    

    Das dumme hierdran ist, dass er jedes mal, wenn er rendert (tut er dauerhast) an der Stelle, wo er ein "\n" findet, die if-Abfrage ausführt. Sprich er verzieht alles und geht gar nicht.
    Wie gesagt der einzige Code der das echt richtig anzeigt und alles klappt bis auf das löschen ist

    if (keyOut[x] == '\n')
            {
                keyOut[x] = '_';
    
                for(int a=keyOut.size(); a<(chars*curLine); a++)
                {
                    keyOut += '_';
                }
            }
    


  • Sprich er verzieht alles und geht gar nicht

    und was bedeutet das konkret?



  • er zeichnet normalerweise wenn alles richtig läuft jede einzelne taste auf die weise

    1  2  3  4  5  6  7  8  9
    10 11 12 13 14 15 16 17 18  usw.
    

    wenn ich jetzt mit meiner bisherrigen variante mache, dann setzt er zum Beispiel bei 6 einen umbruch und füllt bis 9 alle mit Leerzeichen, sodass er wieder in der neuen ist.

    bei der anderen variante, sieht es ungefähr so aus

    1.                          1 2 3 4 5 6(Umbruch)
    2.               789101112
    3.   131415161718192021222324
    4.   252627282930313233343536
    

    also mit jeder taste, die hinzukommt, rückt er die zweite und die 3 dritte zeile einen nach links und jetzt an die letzte zeile die neue taste dran.

    mir ist außerdem aufgefallen, das er dieses prinzip die ganze zeit ausfürht jedoch schreibt er in die zweite zeile nur so viele zeichen, wie bei der ersten fehlen und bei den anderen macht er wieder die max. anzahl.
    aber das verrücken macht er die ganze zeit



  • jedoch schreibt er in die zweite zeile nur so viele zeichen, wie bei der ersten fehlen

    weil dann das hier greift:

    //Wenn eine Reihe voll ist, sprich 40 Zeichen, dann mache automatisch einen Umbruch
    if(x == chars*curLine)
    {
      curLine++;
      glTranslatef(-size.X,-charSize.Y,0);
    }
    

    du brauchst also einen zaehler der die anzahl der zeichen der aktuellen zeile enthaelt.

    also mit jeder taste, die hinzukommt, rückt er die zweite und die 3 dritte zeile einen nach links und jetzt an die letzte zeile die neue taste dran.

    zaehlst du evtl das '\n'-zeichen mit?



  • zu 1. okay werde ich mal gucken was man da machen kann

    zu 2. ich gehe mal von aus das er das tut, weil er den string ja immer wieder durchlaufen muss, und sobald er auf ein \n trifft, führt er die if-abfrage aus.
    Wenn ich jetzt wie schon bei meinem anderen Versuch den Umbruch zum Beispiel zu einem Leerzeichen mache, dann macht er gar nichts erst, weil er beim 2. rendern die restlichen auffüllt



  • ich gehe mal von aus das er das tut

    wuerdest du den debugger benutzen, waerst du sicher...

    vorschlag:

    void draw(char *text)
    {
    	while (*text)
    	{
    		glPushMatrix();
    
    		// eine zeile schreiben	(maximal "maximum" zeichen)
    		for (int chars= 0; chars<maximum; chars++)
    		{
    			if (*text=='\n' || *text==0) // zeile zuende wenn zeilenumbruch oder textende
    				break;
    
    			drawchar(*text); // zeichen zeichnen
    			glTranslatef(zeichenAbstand, 0.0, 0.0); // zum naechsten zeichen
    			text++; 
    		}
    		glPopMatrix(); // zurueck zum zeilenanfang
    		glTranslatef(0.0, zeilenAbstand, 0.0); // naechste zeile
    	}
    }
    


  • also die variante klappt auch nicht
    aber ich hatte eine gute idea die klappen dürfte

    eine weitere frage habe ich noch:
    wie kann ich das letzte zeichen einen strings ermitteln?


  • Mod

    mit strlen(...)-1, wobei du checken solltest ob strlen >0 liefert.



  • Du solltest dich nochmal ein bisschen mit den Grundlagen beschaeftigen, wenn du solche einfachen Sachen nicht hinbekommst. Das ist echt einfachste Arbeit mit Pointern/ Arrays. Sowas kann man auch alles in Konsolenprogrammen testen. f'`8k

    Autocogito

    Gruß, TGGC (making great games since 1992)


Anmelden zum Antworten