1

I am currently trying to figure something out. For my world editor I want my program to read a text file and use its content as code material. I've already made a decent file reader but now I've got a problem. In the console I am getting the right output, the file has only one line that says:

this.makeGrass(new Vector3f(0, 1, 2));

this is actually part of a code that tells my program to render a specific object to the scene, in this case it's a grass model. However instead of just printing this information to the console with

System.out.println(aryLines[i]);

I want to be able to use the information stored on the .txt file so I can actually add it to my rendering code. The entire method that prints the lines on the text file to the console is:

     public void TextOutput()
     {
        String file_name = "C:/Text.txt";

        try
        {
            StoreCoords file = new StoreCoords(file_name);
            String[] aryLines = file.OpenFile();

            int i;
            for (i = 0; i < aryLines.length; i++)
            {
                System.out.println(aryLines[i]);
            // !! How to use the information as part of my code ??
            }
        } catch(IOException e)
        {
            System.out.println(e.getMessage());
        }
     }

I hope you understand what I want: The content of my text file is a piece of code that I want to use further instead of having it just print to the console, I'm sure this is possible but I wouldn' know how.

Bhargav Rao
  • 50,140
  • 28
  • 121
  • 140
DisasterCoder
  • 477
  • 1
  • 3
  • 17
  • I found this which may help you: http://stackoverflow.com/questions/1057796/executing-java-code-given-in-a-text-file and this: http://stackoverflow.com/questions/6226063/run-a-simple-text-file-as-java – DigitalNinja Jul 18 '15 at 00:42
  • This is not the way programs are to be written in Java. Code is not supposed to be loaded dynamically and then executed, and most (if not all) problems can be solved with non-changing sources. – fps Jul 18 '15 at 06:20

3 Answers3

1

As Java is a compiled language, you'd have to recompile at runtime and I am not sure that is even possible. If I were you, I'd hardcode in my own commands. You want to call a function called makeGrass, hardcode it in. Maybe in your text file you can have this:

    makeGrass:0,1,2

Then have this right after the println:

    if(aryLines[i].startsWith("makeGrass:")) {
            String Arguments = aryLines[i].substring(aryLines[i].indexOf(":")+1, aryLines[i].length());
            ArgArray = Arguments.split(",");
            this.makeGrass(new Vector3f(Double.parseDouble(ArgArray[0]), Double.parseDouble(ArgArray[1]), Double.parseDouble(ArgArray[2])));
    }

I'm going to leave my answer like this, assuming you are an experienced programmer. If I am wrong feel free to ask and I will explain it to you. I can also explain how to modify it to add different commands if you want.

Also, this is rather unsafe because if the input is in the wrong format it will crash the app. If you plan on letting users edit the file, then I can show you how to add on safeties.

Hope this helped, Joseph Meadows

Joseph Meadows
  • 160
  • 2
  • 8
  • Thanks, I think what you suggest is getting close to what I am looking for, maybe I should explain a bit better what my intensions were. My program is a world editor and instead of positioning every object through code by defining it with: this.makeGrass(new Vector3f(x,y,z)); I want to change the position inside the program and save the new coordinates upon hitting some key on the keyboard (its like a game save) for that reason I wanted the program to create a text file with the respective code that has the new coordinates and then let java read and "load " the new position upon restart. – DisasterCoder Jul 18 '15 at 07:40
  • Okay I was about to try out what you suggested, however I am not getting it to work. I am not that of an experienced programmer so maybe I'm just missing something simple but it gives me an error for ArgArray, what do I have to do in order to make it work? – DisasterCoder Jul 18 '15 at 08:04
  • Mother of god, is worked!! I had to teak my Vector3f class a bit, I'm going to post the answer now and maybe someone can tell me how I can make it simpler (instead of making a new constructor.. – DisasterCoder Jul 18 '15 at 08:24
1

Okay, thanks to Joseph Meadows for the hint, I'm doing the following thing, right after the println statement I've added the code provided by him. To make ArgArray work I had to put String[] before it and also I had to create a new constructor in my Vector3f class to match the Double.parseDouble thingy..

public void TextOutput()
     {   
        String file_name = "C:/Users/Server/Desktop/textText.txt";

        try
        {           
            StoreCoords file = new StoreCoords(file_name);
            String[] aryLines = file.OpenFile();

            int i;
            for (i = 0; i < aryLines.length; i++)
            {
                System.out.println(aryLines[i]);    

                 if(aryLines[i].startsWith("makeGrass:")) {
                        String Arguments = aryLines[i].substring(aryLines[i].indexOf(":")+1, aryLines[i].length());
                        String[] ArgArray = Arguments.split(",");

                        this.makeGrass(new Vector3f(Double.parseDouble(ArgArray[0]), 
                                                    Double.parseDouble(ArgArray[1]), 
                                                    Double.parseDouble(ArgArray[2])));
                }
            }
        } catch(IOException e)
        {
            System.out.println(e.getMessage());
        }
     }

my original Vector3f constructor is:

public Vector3f(float x, float y, float z)
    {
        this.m_x = x;
        this.m_y = y;
        this.m_z = z;
    }

and to make the code in the TextOutput method work I've added another constructor right below the original one..

public Vector3f(double parseDouble, double parseDouble2, double parseDouble3) {
        this.m_x = (float) parseDouble;
        this.m_y = (float) parseDouble2;
        this.m_z = (float) parseDouble3;
    }

Now everything works great, the console gives me the apropriate statement

makeGrass:0,1,2

and the rendering system creates the grass model at the apropriate coordinates, the only thing I want to change now is that I don't have to add an additional constructor to the Vector3f class, I'm sure I'll figure that out too.

In the picture provided in this link you can see exactly what's going on:

http://www.pic-upload.de/view-27720774/makeGrassEx.png.html

As you can see, the content of the text file is printed out in the console (the numbers below is the fps counter) and the coordinates provided by the text file are interpreted correctly, two grass models being displayed at the respective coordinates which is exactly what I wanted!

Thanks again for your help Joseph Meadows, this is exactly what I was looking for!

DisasterCoder
  • 477
  • 1
  • 3
  • 17
0

I am not sure if you solved this yet, but you did not need the second constructor. I was unsure of the data type you were using for the coordinates, and I assumed you use doubles because that is what I have grown accustomed to using.

In actuality, all types can be parsed from a string. Look here:

    this.makeGrass(new Vector3f(Double.parseDouble(ArgArray[0]), 
                                Double.parseDouble(ArgArray[1]), 
                                Double.parseDouble(ArgArray[2])));

This right now is turning the string into a double. That is what

    Double.parseDouble();

does.

It looks like you are using floats though, so you can always just use the float parsing method:

    Float.parseFloat("String");

That would result with this:

    this.makeGrass(new Vector3f(Float.parseFloat(ArgArray[0]), 
                                Float.parseFloat(ArgArray[1]), 
                                Float.parseFloat(ArgArray[2])));

Sorry for the late response, and you are surely welcome for the help. I just love being useful!

Joseph Meadows
  • 160
  • 2
  • 8