Created
May 15, 2015 15:22
-
-
Save anonymous/62f3832ceeeecc7bf714 to your computer and use it in GitHub Desktop.
test
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import bpy | |
import bgl | |
import blf | |
import bmesh | |
from mathutils import Vector, Matrix | |
from collections import defaultdict | |
from sverchok.utils import ( | |
sv_bmesh_utils, csg_core, csg_geom) | |
from csg_core import CSG | |
from sv_bmesh_utils import pydata_from_bmesh, bmesh_from_pydata | |
Scene = bpy.types.Scene | |
def generate_draw_geometry(caller, context): | |
obj = bpy.context.edit_object | |
me = obj.data | |
bm = bmesh.from_edit_mesh(me) | |
original_face = bm.faces.active | |
verts = [v.co.copy() for v in original_face.verts] | |
face_normal = original_face.normal.copy() | |
bm.free() | |
del bm | |
return verts, face_normal, obj.matrix_world.copy() | |
def generate_boolean_geom(verts, normal, scalar): | |
bm = bmesh.new() | |
final_verts = [] | |
num_verts = len(verts) | |
faces = [] | |
face1 = [] | |
face2 = [] | |
ftwix = [] | |
for idx, v in enumerate(verts): | |
final_verts.append(v) | |
face1.append(idx) | |
for idx, v in enumerate(verts, num_verts): | |
final_verts.append(v + (normal * scalar)) | |
face2.append(idx) | |
for idx, _ in enumerate(verts): | |
idx_1 = idx | |
idx_2 = (idx + 1) % num_verts | |
idx_3 = ((idx + 1) % num_verts) + num_verts | |
idx_4 = idx + num_verts | |
ftwix.append([idx_1, idx_2, idx_3, idx_4]) | |
faces.append(face1) | |
faces.append(face2) | |
faces.extend(ftwix) | |
return final_verts, faces | |
def generate_result(VA, PA, VB, PB): | |
a = CSG.Obj_from_pydata(VA, PA) | |
b = CSG.Obj_from_pydata(VB, PB) | |
faces = [] | |
vertices = [] | |
recursionlimit = sys.getrecursionlimit() | |
sys.setrecursionlimit(10000) | |
try: | |
polygons = a.subtract(b).toPolygons() | |
except RuntimeError as e: | |
raise RuntimeError(e) | |
sys.setrecursionlimit(recursionlimit) | |
for polygon in polygons: | |
indices = [] | |
for v in polygon.vertices: | |
pos = [v.pos.x, v.pos.y, v.pos.z] | |
if not (pos in vertices): | |
vertices.append(pos) | |
index = vertices.index(pos) | |
indices.append(index) | |
faces.append(indices) | |
return vertices, faces | |
def draw_callback_px(self, context, res): | |
verts, fnorm, fmatrix = res | |
scn = context.scene | |
scalar = scn.BGL_OFFSET_SCALAR | |
# 50% alpha, 2 pixel width line | |
bgl.glEnable(bgl.GL_BLEND) | |
bgl.glLineWidth(context.scene.BGL_DEMO_PROP_THICKNESS) | |
bgl.glColor4f(0.8, 0.3, 0.9, 1.0) | |
bgl.glBegin(bgl.GL_LINE_LOOP) | |
for vert in verts: | |
co = fmatrix * (vert + (fnorm * scalar)) | |
bgl.glVertex3f(*co) | |
bgl.glEnd() | |
# restore opengl defaults | |
bgl.glLineWidth(1) | |
bgl.glDisable(bgl.GL_BLEND) | |
bgl.glColor4f(0.0, 0.0, 0.0, 1.0) | |
class ModalDrawOperator(bpy.types.Operator): | |
bl_idname = "view3d.bgl_demo_modal_operator" | |
bl_label = "Simple Modal View3D Operator" | |
def modal(self, context, event): | |
context.area.tag_redraw() | |
if event.type in {'MIDDLEMOUSE'}: | |
return {'RUNNING_MODAL'} | |
if event.type in {'RIGHTMOUSE', 'ESC'}: | |
bpy.types.SpaceView3D.draw_handler_remove(self._handle, 'WINDOW') | |
return {'CANCELLED'} | |
if event.type in {'RET'}: | |
VB, PB = generate_boolean_geom(verts, normal, scalar) # extract this | |
bm = bmesh.from_mesh(context.active_object.data) # from this | |
VA, PA = pydata_from_bmesh(bm) | |
v, f = generate_result(VA, PA, VB, PB) | |
bm.free() | |
bm = bmesh_from_pydata(v, [], f) | |
bm.to_mesh(active_object.data) | |
bm.free() # free and prevent further access | |
return {'FINISHED'} | |
return {'PASS_THROUGH'} | |
def invoke(self, context, event): | |
if context.area.type == 'VIEW_3D': | |
scn = context.scene | |
scn.BGL_OFFSET_SCALAR = 5 | |
scn.BGL_DEMO_PROP_THICKNESS = 0.0 | |
res = generate_draw_geometry(self, context) | |
args = (self, context, res) | |
draw_handler_add = bpy.types.SpaceView3D.draw_handler_add | |
self._handle = draw_handler_add( | |
draw_callback_px, args, 'WINDOW', 'POST_VIEW') | |
bpy.ops.object.mode_set(mode='OBJECT') | |
context.active_object.show_wire = True | |
context.active_object.show_all_edges = True | |
context.window_manager.modal_handler_add(self) | |
return {'RUNNING_MODAL'} | |
else: | |
self.report({'WARNING'}, "View3D not found, cannot run operator") | |
return {'CANCELLED'} | |
class HelloWorldPanel(bpy.types.Panel): | |
"""Creates a Panel in the Object properties window""" | |
bl_label = "Hello World Panel" | |
bl_idname = "OBJECT_PT_hello" | |
bl_space_type = 'VIEW_3D' | |
bl_region_type = 'UI' | |
# bl_context = "object" | |
def draw(self, context): | |
layout = self.layout | |
col = layout.column() | |
col.prop(context.scene, 'BGL_DEMO_PROP_THICKNESS', text='thickness') | |
col.prop(context.scene, 'BGL_OFFSET_SCALAR', text='amount') | |
col.operator("view3d.bgl_demo_modal_operator") | |
def register(): | |
Scene.BGL_DEMO_PROP_THICKNESS = bpy.props.IntProperty(default=1, max=5) | |
Scene.BGL_OFFSET_SCALAR = bpy.props.FloatProperty( | |
min=-5.0, max=5.0, default=0.0) | |
bpy.utils.register_class(HelloWorldPanel) | |
bpy.utils.register_class(ModalDrawOperator) | |
def unregister(): | |
bpy.utils.unregister_class(HelloWorldPanel) | |
bpy.utils.unregister_class(ModalDrawOperator) | |
del Scene.BGL_OFFSET_SCALAR | |
del Scene.BGL_DEMO_PROP_THICKNESS | |
if __name__ == "__main__": | |
register() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment