Welcome to mirror list, hosted at ThFree Co, Russian Federation.

utils.py « space_view3d_math_vis - git.blender.org/blender-addons.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
blob: be106f18795f4822990ac6864e14e13d2a2ea4c8 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
# SPDX-License-Identifier: GPL-2.0-or-later

import bpy


def console_namespace():
    import console_python
    for window in bpy.context.window_manager.windows:
        for area in window.screen.areas:
            if area.type == 'CONSOLE':
                for region in area.regions:
                    if region.type == 'WINDOW':
                        console = console_python.get_console(hash(region))
                        if console:
                            return console[0].locals
    return {}


def is_display_list(listvar):
    from mathutils import Vector

    for var in listvar:
        if not isinstance(var, Vector):
            return False
    return True


class VarStates:

    @staticmethod
    def store_states():
        # Store the display states, called upon unregister the Add-on
        # This is useful when you press F8 to reload the Addons.
        # Then this function preserves the display states of the
        # console variables.
        state_props = bpy.context.window_manager.MathVisStatePropList
        variables = get_math_data()

        for index, state_prop in reversed(list(enumerate(state_props))):
            if state_prop.name not in variables:
                # Variable has been removed from console
                state_props.remove(index)

        for key, ktype in variables.items():
            if key and key not in state_props:
                prop = state_props.add()
                prop.name = key
                prop.ktype = ktype.__name__
                prop.state = [True, False]

    @staticmethod
    def get_index(key):
        index = bpy.context.window_manager.MathVisStatePropList.find(key)
        return index

    @staticmethod
    def delete(key):
        state_props = bpy.context.window_manager.MathVisStatePropList
        index = state_props.find(key)
        if index != -1:
            state_props.remove(index)

    @staticmethod
    def toggle_display_state(key):
        state_props = bpy.context.window_manager.MathVisStatePropList
        if key in state_props:
            state_props[key].state[0] = not state_props[key].state[0]
        else:
            print("Odd: Can not find key %s in MathVisStateProps" % (key))

    @staticmethod
    def toggle_lock_state(key):
        state_props = bpy.context.window_manager.MathVisStatePropList
        if key in state_props:
            state_props[key].state[1] = not state_props[key].state[1]
        else:
            print("Odd: Can not find key %s in MathVisStateProps" % (key))


def get_math_data():
    from mathutils import Matrix, Vector, Quaternion, Euler

    locals = console_namespace()
    if not locals:
        return {}

    variables = {}
    for key, var in locals.items():
        if len(key) == 0 or key[0] == "_":
            continue

        type_var = type(var)

        # Rules out sets/dicts.
        # It's also possible the length check below is slow
        # for data with underlying linked-list structure.
        if not hasattr(type_var, "__getitem__"):
            continue

        # Don't do a truth test on the data because this causes an error with some
        # array types, see T66107.
        len_fn = getattr(type_var, "__len__", None)
        if len_fn is None:
            continue
        if len_fn(var) == 0:
            continue

        if isinstance(var, (Matrix, Vector, Quaternion, Euler)) or \
           isinstance(var, (tuple, list)) and is_display_list(var):

            variables[key] = type_var

    return variables


def cleanup_math_data():

    locals = console_namespace()
    if not locals:
        return

    variables = get_math_data()

    for key in variables.keys():
        index = VarStates.get_index(key)
        if index == -1:
            continue

        state_prop = bpy.context.window_manager.MathVisStatePropList.get(key)
        if state_prop.state[1]:
            continue

        del locals[key]
        bpy.context.window_manager.MathVisStatePropList.remove(index)


def console_math_data():
    from mathutils import Matrix, Vector, Quaternion, Euler

    data_matrix = {}
    data_quat = {}
    data_euler = {}
    data_vector = {}
    data_vector_array = {}

    for key, var in console_namespace().items():
        if key[0] == "_":
            continue

        state_prop = bpy.context.window_manager.MathVisStatePropList.get(key)
        if state_prop:
            disp, lock = state_prop.state
            if not disp:
                continue

        if isinstance(var, Matrix):
            if len(var.col) != 4 or len(var.row) != 4:
                if len(var.col) == len(var.row):
                    var = var.to_4x4()
                else:  # todo, support 4x3 matrix
                    continue
            data_matrix[key] = var
        elif isinstance(var, Vector):
            if len(var) < 3:
                var = var.to_3d()
            data_vector[key] = var
        elif isinstance(var, Quaternion):
            data_quat[key] = var
        elif isinstance(var, Euler):
            data_euler[key] = var
        elif type(var) in {list, tuple} and is_display_list(var):
            data_vector_array[key] = var

    return data_matrix, data_quat, data_euler, data_vector, data_vector_array