import bpy
import time
import random
import math
import pickle
import typing
# from .general import DirectionalPoint2d, Rect2d, DirectionalPoints2dCollection
# from ..utils import définirPixel
from bpy.types import Node
from .. import CityNodeTreeNode, Taggable
from .datablock import Datablock


class DatablockEtTransform():
	def __init__(self):
		# self.datablock: Datablock = None # Python 3.6+ uniquement, Blender 2.79 est encore à Python 3.5 malheureusement
		self.datablock = None  # type: Datablock
		self.position = (0, 0, 0)
		self.rotation = (0, 0, 0)
		self.scale = (1, 1, 1)


class Building(Taggable):
	'''Un bâtiment consiste en plusieurs sc_bldata_list à instancer (avec une transformation pour chacun), et une taille'''

	def __init__(self):
		Taggable.__init__()
		# self.datablocks_et_transforms = []
		self.taille_type = None  # FIXED, VARIABLE_MIN_MAX
		self.taille_fixe_grid = (10, 10)
		self.taille_variable_min_grid = (10, 10)
		self.taille_variable_max_grid = (10, 10)
		self.tags = None  # string

	def get_datablocks_et_transforms(self) -> typing.List[DatablockEtTransform]:
		a = DatablockEtTransform()
		b = pickle.loads(eval(''))  # type: DatablockEtTransform


class BuildingNodeAddDatablockSocketOperator(bpy.types.Operator):
	bl_idname = 'node.building_node_add_datablock_socket'
	bl_label = 'Add datablock'
	bl_description = 'Add a datablock to this building, such as a mesh or object group'
	source_node_path = bpy.props.StringProperty()

	def execute(self, context):
		source_node = eval(self.source_node_path)
		random_string = time.time()
		source_node.inputs.new('OptionalDatablockSocket', str(random_string))
		return {'FINISHED'}


class BuildingNode(Node, CityNodeTreeNode):
	bl_label = 'Building'
	taille_type = bpy.props.EnumProperty(
		name='Size type',
		description='',
		items=[
			('FIXED', 'Fixed', '', 1),
			('VARIABLE_MIN_MAX', 'Variable min - max', '', 2),
		])
	taille_fixe_grid = bpy.props.IntVectorProperty(
		name='Size',
		description='On x and y, in city grid cells', default=(1, 1), size=2)
	taille_min_grid = bpy.props.IntVectorProperty(
		name='Size min',
		description='On x and y, in city grid cells', default=(1, 1), size=2)
	taille_max_grid = bpy.props.IntVectorProperty(
		name='Size max',
		description='On x and y, in city grid cells', default=(4, 4), size=2)
	user_data = bpy.props.StringProperty(
		name='Tags',
		description='Set your custom data here. They act like tags, and can be used by various algorithms further down in the graph hierarchy. Check the doc '
					'for more information.', )
	pickled_building = bpy.props.StringProperty()

	def init(self, context):
		self.width = 300
		# self.inputs.new('DatablockSocket', 'Datablock')
		self.outputs.new('CityAssetSocket', 'Building')

	def draw_buttons(self, context, layout):
		row = layout.row()
		row.prop(self, 'taille_type')
		if self.taille_type == 'FIXED':
			row = layout.row()
			row.prop(self, 'taille_fixe_grid')
		else:
			row = layout.row()
			row.prop(self, 'taille_min_grid')
			row = layout.row()
			row.prop(self, 'taille_max_grid')
		row = layout.row()
		row.prop(self, 'user_data')
		op = layout.operator('node.building_node_add_datablock_socket')
		op.source_node_path = 'bpy.data.node_groups["' + self.id_data.name + '"].' + self.path_from_id()

	def update(self):
		pass
# datablock = Datablock()
# datablock.type = self.datablock_type
# datablock.name = self.datablock_name
# datablock.user_data_string = self.user_data
# ne pas évaluer le user data maintenant, à cause du random.seed qui pourra être ainsi défini plus tard si besoin
# pickled_Datablock = str(pickle.dumps(datablock))
