0
$\begingroup$

I think I know this is a basic question but I dont got the connection between values inside a class and outside.

I have an Array with string values defined in a OperatorClass and I can use it inside but what I really want is defining the Array Values outside of the class and then reference it when needed - everytime I define a PropertyGroup or StringProperty I cant find it...

I think I miss some basic understanding where values are stored in that blender data structure or how to add the array to some kind of globalness…

EDIT: so I would like to outsource the Arrays from this class

class OBJECT_OT_createWorkFolder(bpy.types.Operator):
    bl_idname = "object.workfoldbtn"
    bl_label = "Create Projectfolder"
    bl_description = "Fügt dem Ausgew. Verzn. Arbeitsfolder hinzu"

    Workfolder = ["00_DATA","01_INCOMING","02_Workspace","03_Render","04_Compositing","05_OUT"]
    WS_Subfolder = ["02_0_Exports","02_1_Assets", "02_2_Textures","02_3_Light","02_4_Scripts","02_x_Caches"]
    Rndr_Subfolder = ["03_0_TestRender","03_1_FINAL"]
    Comp_Subfolder = ["Photoshop","AfterEffects","DaVinciRes"]
...
$\endgroup$
2
  • $\begingroup$ You can just add a list (array), dict or set as usual to your script and use a callback to get the values when calling the operator, easy. If you want user interaction use a CollectionProperty: blender.stackexchange.com/a/30446/31447. What's your goal? What exactly you can't find? $\endgroup$
    – brockmann
    Commented Apr 1, 2020 at 12:26
  • $\begingroup$ Thx for the link I think I got through this in the past, but I will give it a next try. .. PS: I edited the Question, to what I want mor exactly $\endgroup$ Commented Apr 1, 2020 at 12:35

2 Answers 2

2
$\begingroup$

Two methods:

  1. Method 1: python way
import bpy

arr = ["string1", "string2"]

class ClassName(bpy.types.Operator):

    def execute(self, context):
        for str in arr:
        print(str)

    return {'FINISHED'}

classes = (
    ClassName,
)

def register():
    from bpy.utils import register_class
    for cls in classes:
        register_class(cls)

def unregister():
    from bpy.utils import unregister_class
    for cls in reversed(classes):
        unregister_class(cls)

if __name__ == "__main__":
    register()

  1. Method 2: Blender way
import bpy

class Variables(bpy.types.PropertyGroup):
    string1: bpy.props.StringProperty(name="a string")
    string2: bpy.props.StringProperty(name="another string", default="default value")

class ClassName(bpy.types.Operator):

    def execute(self, context):
        bpy.context.scene.var.string1 = "Hello World"
        print(bpy.context.scene.var.string1)
        print(bpy.context.scene.var.string2)

    return {'FINISHED'}


classes = (
    ClassName,
    Variables,
)

def register():
    from bpy.utils import register_class
    for cls in classes:
        register_class(cls)
    bpy.types.Scene.var = bpy.props.PointerProperty(type=Variables)

def unregister():
    from bpy.utils import unregister_class
    for cls in reversed(classes):
        unregister_class(cls)      
    del bpy.types.Scene.var

if __name__ == "__main__":
    register()


learnt from: Godot Game Tools

edit: python console this is how you can access a variable in blender from anywhere. I've used GodotGameTools as an example and also highlighted what it should have been if you used my code

$\endgroup$
4
  • $\begingroup$ thx for the efford but can you show an example "the Blender Way" without using single strings and putting all in an Array ? … Or does the python way mean, that an array that is created somewhere can addressed everywhere ? $\endgroup$ Commented Apr 1, 2020 at 12:46
  • $\begingroup$ @MasterHeavy I don't think you can store arrays of strings easily, especially arrays of varying lengths. The simplest would be to store all the elements in a single string with a separator like '|', then use a method to parse and unparse it to get all your elements with the string.split('|') method. $\endgroup$
    – Gorgious
    Commented Apr 1, 2020 at 15:29
  • $\begingroup$ This: blender.stackexchange.com/questions/16511/… - seems to be what I need, but I cant sort it out and use it for my case - he has this array and can use it... I am confused $\endgroup$ Commented Apr 1, 2020 at 19:16
  • $\begingroup$ "seems what I need" is the use of CollectionProperty as mentioned in my comment years ago @MasterHeavy To me it seems you don't need that because your list is hard coded and unique so you just can declare a set, done. Again, in case you'd like to have user interaction (changing the list), let me know... $\endgroup$
    – brockmann
    Commented Apr 2, 2020 at 9:24
0
$\begingroup$

This may be a stupid hack and its performance might be poor, but I find it quite transparent and usable.

I store the list in a textblock:

# a Text data-block named 'y' must be present. 
# done in 2.79b

import bpy

cool_data = ["isn't", "this", "amazing"] # example list to be stored

def store_list(x):
    t = bpy.data.texts["y"] # access the Text data-block
    t.clear() # empty the Text data-block
    counter = 0 # watch out for the last line
    end = len(x) # length of the list
    s = "\n" # separator
    for a in x: # go through the list
        if counter == end - 1:
            s = "" # if it's the last item in the list, don't start a new line
        t.write(str(a) + s) # write the data into the Text data-block
        counter += 1

def retrieve_list():
    b = [] # list to be returned as a result
    t = bpy.data.texts["y"] # access to the Text data-block
    for a in t.lines: # go through all lines of the Text
        b.append(a.body) # add the line's content to the list (might need conversion)
    return b # return the list


# save the list in the Text data-block
store_list(cool_data)

# retrieve the list
cooler_data = retrieve_list()


# check results
print(cool_data)
print(cooler_data)

enter image description here

Depending on the list in question, you may need to parse it properly, encode it, it's not a cure-all for fancier lists, there are certainly a lot of quicker ways to store it. But I find that making a readable text has huge advantages for the occasional coder who isn't coding every week and who's lists usually contain numbers or text instead of complex objects. Many ways to do it fancier. Storing the list in just one line, letting the script create the Text data-block automatically etc.

$\endgroup$

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .