1
$\begingroup$

I'm trying to get information from a Blend File, but I've just hit a wall.

We are referring to Blender Internal Render. Not Cycles Render.

I'm new to Blender basically, so I really don't have a clue of neither scripting or Python whatsoever, so I really don't have a clue of what do I have access or what can or can't do via Python scripts on Blender, so I was thinking: Is it possible to take the material information from a Blend file or from within Blender, specifically, what files they are using?

enter image description here

In this example, thanks to Blender, I know the files the Metal material is using are these, but is there a way to output, let's say:

Metal: - nomad_a1_diff.tga - nomad_a1_norm.tga - enviroment.png

And this, with all materials? Thank you in advance!

EDIT

What I'm basically trying to get is this

  • Name of any materials of a mesh.
  • Listing the textures of that single material.

Example

Material: Metal Textures of the Material Metal: nomad_a1_diff.tga, nomad_a1_norm.tga, enviroment.png

These three are the materials for that Metal material on the image.

I want to do this with every material on the model. Thanks to this script, I've got the name of all the materials, however, instead of listing all the textures per material, it lists all the textures of the model, I don't need that.

UPDATE

Thanks to atomicbezierslinger for the script, he helped me to get a step on the right direction!

I've run your script, but it gives me just the name of the textures. I've done some research and found a function called bpy.data.materials so I decided to add it to the script and now it looks like this

import bpy
import datetime

def inspect_textures():
    for t in bpy.data.materials:
        print(t.name)
        for t in bpy.data.textures:
            if isinstance(t, bpy.types.ImageTexture) and hasattr(t,'image'):
                x = t.image
                if hasattr(x,'filepath'):
                    print(t.name, type(t),t.image.filepath)                       
        else:
             print(t.name, type(t), "?")



inspect_textures()

enter image description here

This is the output from the code above. Now it gives the name of the material and the name of all the textures of the model, when all what I need is the texture names of the specific materials, is there something else it can be done or does it need another import? Thanks so far for the help!

$\endgroup$
  • $\begingroup$ It will be better form if the first variable (t) were change to the letter (m) since that would semantically be close to the word (m)aterial. Change the second line to match. Actually I think your use of material is incorrect. That outter loop should be deleted. $\endgroup$ – atomicbezierslinger May 24 '16 at 21:21
  • $\begingroup$ It would be useful to add two statements to your requirements as bullet points. Example. 01 Please include X, Y, and Z. 02 Please exclude T, U, V. Currently I do not understand what the I need to understand. Please explain and rewrite .... [specific materials] $\endgroup$ – atomicbezierslinger May 24 '16 at 21:31
  • $\begingroup$ *Editing post* $\endgroup$ – TotalNoob May 24 '16 at 21:32
  • $\begingroup$ I've edited the post with the points, thanks for pointing it out $\endgroup$ – TotalNoob May 24 '16 at 21:40
1
$\begingroup$

enter image description here

A Text Editor window containing a Python Script. Filename indicated has the suffix [.py]. Line numbers and Syntax Coloring enabled. Yellow arrows from left to right show, Window Type, Name of file, Buttons for line numbers and syntax coloring, Button to Run Script. Image Above.

Only copy the newest software code sample. The images above have older software. But they address questions that may apply to you which are not letter by letter code specific.

NEWER

import bpy
import datetime

print("-" * 88)
print(datetime.datetime.now())
print("-" * 88)

def inspect_m_textures(simple_sleek):
    print(bpy.types.ImageTexture, " Preferred")
    for m in bpy.data.materials:
        #print("M ", m.name)
        b = False;
        for ts in m.texture_slots:
            if hasattr(ts, 'name'):
                b = True
                continue
        if b:
            print("M ", m.name)
            inspect_t_textures(simple_sleek, m.texture_slots)


def inspect_t_textures(simple_sleek, slots):
    #print(bpy.types.ImageTexture, " Preferred")
    n = 0
    fs = "%03d" # format string
    #for t in bpy.data.textures:
    for ts in slots:
        #print(t.name)
        #print(type(t))
        #n += 1
        if not hasattr(ts, 'name'):
            continue
        t = ts.texture
        if isinstance(t, bpy.types.ImageTexture) and hasattr(t,'image'):
            n += 1
            ns = fs % (n,)
            if hasattr(t,'image'):
                x = t.image
                if hasattr(x,'filepath'):
                    print(ns, t.name, t.image.name,t.image.filepath)
                else:
                    print(ns, t.name, "Incomplete", "Incomplete")
            else:
                print(ns, t.name, "No Image")
        elif not simple_sleek:
            n += 1
            ns = fs % (n,)
            print(ns, t.name, type(t), "Other No Match")



inspect_m_textures(True)    

OLDER

import bpy
import datetime

print("-" * 88)
    print(datetime.datetime.now())
print("-" * 88)

def inspect_textures():
    for t in bpy.data.textures:
        print(t.name)
        #print(type(t))
        if isinstance(t, bpy.types.ImageTexture) and hasattr(t,'image'):
            x = t.image
            if hasattr(x,'filepath'):
                print(t.name, type(t),t.image.filepath)
        else:
             print(t.name, type(t), "?")



inspect_textures()    

Python for Cut and Paste. Code Block Above. Inspect, Verify and Improve. You can delete comments and extra print statements and extra print arguments.

Open or use text editor window. New Text. Name Textures.py . Copy and paste the text above. Make sure the formatting is retained. Execute from Button or Keystroke indicated on Tooltip of Button. The console window has the textual results. Toggle the visibility of the Console Window from the menu. In the [Info] window Menu/Window/Toggle System Console

enter image description here

Console Window on Windows 10. Console allows Copy and Paste. Python allows Standard Out Redirection. Image Above.

enter image description here

Toggle the System Console. Image above.

$\endgroup$
  • $\begingroup$ Thank you very much for your help, I've updated the post with your code and added some information about what I found using another bpy. Thanks so far! $\endgroup$ – TotalNoob May 24 '16 at 20:40
  • $\begingroup$ Suggestion. Vote up if the proposed answer is useful. Vote down otherwise. Vote answer if applicable. $\endgroup$ – atomicbezierslinger May 24 '16 at 21:22
1
$\begingroup$

This is not that difficult in the grand scheme of things. The filepath for the image for the texture in slot one of a selected object is:

C.object.active_material.texture_slots[1].texture.image.filepath

To do what you would like, you would just need to iterate over the objects of each scene, and each texture slot in each material. You will need to check for when there is no material or Texture. This is a super inflexible way to do so:

import bpy

for i in bpy.data.scenes['Scene'].objects:
    print(i.name + ":")
    for mslot in i.material_slots:
        print("\t" + mslot.name + ":")
        if not mslot is None:
            if not mslot.material is None:
                for tslot in mslot.material.texture_slots:
                    if not tslot is None:
                        print("\t\t" + tslot.name + "=>")
                        if hasattr(tslot.texture, 'image'):
                            print ("\t\t\t" + tslot.texture.image.filepath)

Not the most pythonic code ever, I was in the middle of something else.

$\endgroup$
0
$\begingroup$

enter image description here

import bpy
import datetime

def time_stamp():
    print("-" * 88)
    print(datetime.datetime.now())
    print("-" * 88)

class material_texture:
    def __init__(this, name_fp = "?", texturetype_fp=False, image_fp=False, filepath_fp="?"):
        this.name = name_fp
        this.texturetype = texturetype_fp
        this.image = image_fp
        this.filepath = filepath_fp

    def __str__(self):

        return self.name + " , " + str(self.texturetype) + " , " + str(self.image) + " , " + self.filepath

def texture_line(tl):
    n = 0
    fs = "%03d" # format string
    for t in tl:
        n += 1
        ns = fs % (n,)
        print(ns, t)


def inspect_m_textures(simple_sleek):
    print(bpy.types.ImageTexture, " Preferred")

    for m in bpy.data.materials:
        tl = inspect_t_textures(simple_sleek, m.texture_slots)
        ftl = tl
        if (simple_sleek):
            ftl = [t for t in tl if t.texturetype]
        if (len(ftl) > 0):
            print("M ", m.name, "-"*8)
            texture_line(ftl)

def inspect_t_textures(simple_sleek, slots):
    n = 0
    tlist = []
    for ts in slots:
        if not hasattr(ts, 'name'):
            continue
        t = ts.texture
        if isinstance(t, bpy.types.ImageTexture):
            n += 1
            if hasattr(t,'image'):
                x = t.image
                choice = True;
                if (choice):
                    if hasattr(x,'filepath'):
                        x = material_texture(t.name, True, t.image.name, t.image.filepath)
                        tlist.append(x)
                    else:
                        tlist.append(material_texture(t.name, True, True, "Incomplete"))
                else:
                    tlist.append(material_texture(t.name, True, t.image.name, getattr(x, 'filepath', "Incomplete")))

            else:
                tlist.append(material_texture(t.name, True, False, "Incomplete"))
        elif not simple_sleek:
            n += 1
            tlist.append(material_texture(t.name, False, False, "Other No Match"))
    return tlist

def test333():        
    time_stamp()
    inspect_m_textures(False) 
    time_stamp()
    inspect_m_textures(True) 

test333()

Just a low priority alternative to the above selected answer. Some of my test textures were not that well groomed and thus more tests to avoid missing data issues. Also I wanted to use other tests for personal purposes. There is a separation of data query and presentation now. Small testing software rig. The accompanying explanations are in the original selected answer.

$\endgroup$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.