Create vertex and edges using this code?

I have vertex location informatin and edge information but i dont know how to put it into Blender using python. the information was created using a vertice and edge exporter (exports to text)

can that information be somehow imported back into blender using python?

Example: “a0” is the vertex, 1.0, -1.0, 1.0, is the location. [“Vertex”,X,Y,Z]

[“a0”,1.0,-1.0,-1.0],
[“a1”,1.0,-1.0,1.0],
[“a2”,-1.0,-1.0,-1.0],
[“a3”,-1.0,-1.0,1.0],
[“a4”,1.0,1.0,-1.0],
[“a5”,1.0,1.0,1.0],
[“a6”,-1.0,1.0,-1.0],
[“a7”,-1.0,1.0,1.0],

Example: a4 is connected to a0 it is an edge.

[“a4”,“a0”],
[“a4”,“a6”],
[“a4”,“a5”],
[“a0”,“a2”],
[“a0”,“a1”],
[“a2”,“a6”],
[“a2”,“a3”],
[“a6”,“a7”],
[“a5”,“a1”],
[“a5”,“a7”],
[“a1”,“a3”],
[“a3”,“a7”],

0). make an empty BMesh object

  1. Create BMesh verts at the locations given. While you are doing this, make a dictionary which maps your string variable (example - “a3”) to the index of the BMesh vertex which you have created

  2. Generate the edges using your list of edges (eg [“a1”,“a5”]) and your dictionary

I wlll point you toward these examples and references. If you need more explicit code, please post what you have tried and I will help

Addon template with bmesh geometry
https://svn.blender.org/svnroot/bf-blender/trunk/blender/release/scripts/templates_py/operator_mesh_add.py

Bmesh Module documentation. See the samele script
http://www.blender.org/api/blender_python_api_2_75_release/bmesh.html?highlight=bmesh#module-bmesh

Best,
Patrick

Yes, it’s possible. There’s a utility function for this simple case. The script assumes vertices to be sorted and simply casts the numeric part of the vertex names in the edge list to compute the indices:

import bpy

verts_raw = (
    ["a0",1.0,-1.0,-1.0],
    ["a1",1.0,-1.0,1.0],
    ["a2",-1.0,-1.0,-1.0],
    ["a3",-1.0,-1.0,1.0],
    ["a4",1.0,1.0,-1.0],
    ["a5",1.0,1.0,1.0],
    ["a6",-1.0,1.0,-1.0],
    ["a7",-1.0,1.0,1.0],
)

edges_raw = (
    ["a4","a0"],
    ["a4","a6"],
    ["a4","a5"],
    ["a0","a2"],
    ["a0","a1"],
    ["a2","a6"],
    ["a2","a3"],
    ["a6","a7"],
    ["a5","a1"],
    ["a5","a7"],
    ["a1","a3"],
    ["a3","a7"],
)

verts = []
for v in verts_raw:
    verts.append(v[1:])
    
edges = []
for a, b in edges_raw:
    edges.append((int(a[1:]), int(b[1:])))

me = bpy.data.meshes.new("")
me.from_pydata(verts, edges, [])
me.validate()
me.update()

ob = bpy.data.objects.new("", me)
scene = bpy.context.scene
scene.objects.link(ob)
scene.update()

thanks! Do i cope that to notepad and add it to blender addons?

Attachments



thank! it worked I copy and pasted that into blender, just what I needed Cheers.

How would I go about making this an import function? For example I go to Import in Blender I want to Import a .txt file, I import the text file into Blender the same way you would import .obj file or .dae files?

How is the data stored? Single file for vertices and edges? Are both separated somehow?

Assuming it’s a single file without separator…

["a0",1.0,-1.0,-1.0],
["a1",1.0,-1.0,1.0],
["a2",-1.0,-1.0,-1.0],
["a3",-1.0,-1.0,1.0],
["a4",1.0,1.0,-1.0],
["a5",1.0,1.0,1.0],
["a6",-1.0,1.0,-1.0],
["a7",-1.0,1.0,1.0],
["a4","a0"],
["a4","a6"],
["a4","a5"],
["a0","a2"],
["a0","a1"],
["a2","a6"],
["a2","a3"],
["a6","a7"],
["a5","a1"],
["a5","a7"],
["a1","a3"],
["a3","a7"],

… here’s a script based on the Import templates found in Text editor:

import bpy


def read_some_data(context, filepath):
    verts = []
    edges = []
    
    with open(filepath, 'r') as file:
        for line in file:
            s = line.strip("[],
").split(",")
            if len(s) == 4:
                verts.append(map(float, s[1:]))
            else:
                edges.append((int(s[0][2:-1]), int(s[1][2:-1])))

    me = bpy.data.meshes.new("Imported")
    me.from_pydata(verts, edges, [])
    me.validate()
    me.update()

    ob = bpy.data.objects.new("Imported", me)
    context.scene.objects.link(ob)
    context.scene.update()

    return {'FINISHED'}


# ImportHelper is a helper class, defines filename and
# invoke() function which calls the file selector.
from bpy_extras.io_utils import ImportHelper
from bpy.props import StringProperty, BoolProperty, EnumProperty
from bpy.types import Operator


class ImportSomeData(Operator, ImportHelper):
    """This appears in the tooltip of the operator and in the generated docs"""
    bl_idname = "import_test.some_data"  # important since its how bpy.ops.import_test.some_data is constructed
    bl_label = "Import Some Data"

    # ImportHelper mixin class uses this
    filename_ext = ".txt"

    filter_glob = StringProperty(
        default="*.txt",
        options={'HIDDEN'},
    )

    def execute(self, context):
        return read_some_data(context, self.filepath)


# Only needed if you want to add into a dynamic menu
def menu_func_import(self, context):
    self.layout.operator(ImportSomeData.bl_idname, text="Text Import Operator")


def register():
    bpy.utils.register_class(ImportSomeData)
    bpy.types.INFO_MT_file_import.append(menu_func_import)


def unregister():
    bpy.utils.unregister_class(ImportSomeData)
    bpy.types.INFO_MT_file_import.remove(menu_func_import)


if __name__ == "__main__":
    register()


Im not sure if its single file or not, thanks for the code! ill try it out

yes the top one, it looks like that, but i ran into a new problem with some other code the strings look like this, example: [“a1rr”,1.0,-1.0,-1.0], the 1rr is giving me an error. it says something about its not base 10, here is screen shot:


You’ll have to adjust the processing of the input. This can be quite complex if the extra letters make the name unique. If not, just strip all ascii letters.

ok ill try that

It’s actually not so hard with an indirection table. It can be implemented with a simple dict and a counter to enumerate distinct vertex names to be used for the lookup of the names in the edge definition. The assigned counter value is the vertex index, no need to cast anything:

bl_info = {
    "name": "Import Addon",
    "author": "Your Name Here",
    "version": (1, 0),
    "blender": (2, 75, 0),
    "location": "File > Import",
    "description": "...",
    "warning": "",
    "wiki_url": "",
    "category": "Import-Export",
}

import bpy


def read_some_data(context, filepath):
    c = 0
    d = dict()
    verts = []
    edges = []
    
    with open(filepath, 'r') as file:
        for line in file:
            s = line.strip("[],
").split(",")
            if len(s) == 4:
                k = s[0][1:-1]
                try:
                    d[k]
                except KeyError:
                    d[k] = c
                    c += 1
                verts.append(tuple(map(float, s[1:])))
            else:
                k1 = s[0][1:-1]
                k2 = s[1][1:-1]
                edges.append((d[k1], d[k2]))

    me = bpy.data.meshes.new("Imported")
    me.from_pydata(verts, edges, [])
    me.validate()
    me.update()

    ob = bpy.data.objects.new("Imported", me)
    context.scene.objects.link(ob)
    context.scene.update()

    return {'FINISHED'}


# ImportHelper is a helper class, defines filename and
# invoke() function which calls the file selector.
from bpy_extras.io_utils import ImportHelper
from bpy.props import StringProperty, BoolProperty, EnumProperty
from bpy.types import Operator


class ImportSomeData(Operator, ImportHelper):
    """This appears in the tooltip of the operator and in the generated docs"""
    bl_idname = "import_test.some_data"  # important since its how bpy.ops.import_test.some_data is constructed
    bl_label = "Import Some Data"

    # ImportHelper mixin class uses this
    filename_ext = ".txt"

    filter_glob = StringProperty(
        default="*.txt",
        options={'HIDDEN'},
    )

    def execute(self, context):
        return read_some_data(context, self.filepath)


# Only needed if you want to add into a dynamic menu
def menu_func_import(self, context):
    self.layout.operator(ImportSomeData.bl_idname, text="Text Import Operator")


def register():
    bpy.utils.register_class(ImportSomeData)
    bpy.types.INFO_MT_file_import.append(menu_func_import)


def unregister():
    bpy.utils.unregister_class(ImportSomeData)
    bpy.types.INFO_MT_file_import.remove(menu_func_import)


if __name__ == "__main__":
    register()


Thanks! But this is all over my head :o but im learning, ill have to dig deeper into python scripting, is there a website or a wiki I can learn from?