from statistics import mean
import numpy as np
import matplotlib.pyplot as plt
from matplotlib import style

style.use('fivethirtyeight')

xs = np.array([1,2,3,4,5,6], dtype=np.float64)
ys = np.array([5,4,6,5,6,7], dtype=np.float64)

def best_fit_slope_and_intercept(xs, ys):
    m = ( ((mean(xs) * mean(ys)) - mean(xs*ys)) /
          ((mean(xs)*mean(xs)) - mean(xs*xs)) )
    b = mean(ys) - m*mean(xs)
    return m, b

#to find How accurate our Best fit line is
#first find the squared error
def squared_error(ys_orig, ys_line):
    return sum((ys_line - ys_orig)**2)

#then lets find the coefficient of determination or the R theory
def coefficient_of_determination(ys_orig,ys_line):
    y_mean_line = [mean(ys_orig) for y in ys_orig]
    squared_error_regr = squared_error(ys_orig, ys_line)
    squared_error_y_mean = squared_error(ys_orig, y_mean_line)
    return 1 - (squared_error_regr / squared_error_y_mean)

m,b = best_fit_slope_and_intercept(xs,ys)
print ("Slope: ")
print(m)
print("Intercept: ")
print(b)

regression_line = [(m*x)+b for x in xs]

#to print the coefficient of determination
r_squared = coefficient_of_determination(ys, regression_line)
print("Coefficient of determination: ")
print(r_squared)

#to predict just do: predict_x = 8
#                    predict_y = (m*predict_x)+b
#                    plt.scatter(predict_x, predict_y, color='g')

plt.scatter(xs,ys)
plt.plot(xs, regression_line)
plt.show()


"""add oauth

Revision ID: 134b6ad70b5c
Revises: 44775f747bfe
Create Date: 2013-12-04 20:15:30.299940

"""

# revision identifiers, used by Alembic.
revision = '134b6ad70b5c'
down_revision = '44775f747bfe'

from alembic import op
import sqlalchemy as sa

def upgrade():
    ### commands auto generated by Alembic - please adjust! ###
    op.create_table('oauth_clients',
    sa.Column('name', sa.Unicode(length=50), nullable=True),
    sa.Column('description', sa.Unicode(length=300), nullable=True),
    sa.Column('client_id', sa.Unicode(length=100), nullable=False),
    sa.Column('client_secret', sa.Unicode(length=100), nullable=False),
    sa.Column('user_id', sa.Integer(), nullable=False),
    sa.Column('is_confidential', sa.Boolean(), nullable=False),
    sa.Column('redirect_uri', sa.UnicodeText(), nullable=False),
    sa.Column('_default_scopes', sa.UnicodeText(), nullable=True),
    sa.Column('created_at', sa.DateTime(timezone=True), nullable=False),
    sa.ForeignKeyConstraint(['user_id'], ['users.id'], ),
    sa.PrimaryKeyConstraint('client_id')
    )
    op.create_table('tokens',
    sa.Column('id', sa.Integer(), nullable=False),
    sa.Column('token_type', sa.Unicode(length=10), nullable=False),
    sa.Column('client_id', sa.Unicode(length=100), nullable=True),
    sa.Column('user_id', sa.Integer(), nullable=True),
    sa.Column('access_token', sa.Unicode(length=255), nullable=True),
    sa.Column('refresh_token', sa.Unicode(length=255), nullable=True),
    sa.Column('expires', sa.DateTime(timezone=True), nullable=False),
    sa.Column('_scopes', sa.UnicodeText(), nullable=True),
    sa.Column('created_at', sa.DateTime(timezone=True), nullable=False),
    sa.ForeignKeyConstraint(['client_id'], ['oauth_clients.client_id'], ),
    sa.ForeignKeyConstraint(['user_id'], ['users.id'], ),
    sa.PrimaryKeyConstraint('id'),
    sa.UniqueConstraint('access_token'),
    sa.UniqueConstraint('refresh_token')
    )
    op.create_table('grants',
    sa.Column('id', sa.Integer(), nullable=False),
    sa.Column('user_id', sa.Integer(), nullable=True),
    sa.Column('client_id', sa.Unicode(length=100), nullable=False),
    sa.Column('code', sa.Unicode(length=255), nullable=False),
    sa.Column('redirect_uri', sa.UnicodeText(), nullable=True),
    sa.Column('_scopes', sa.UnicodeText(), nullable=True),
    sa.Column('expires', sa.DateTime(timezone=True), nullable=False),
    sa.Column('created_at', sa.DateTime(timezone=True), nullable=False),
    sa.ForeignKeyConstraint(['client_id'], ['oauth_clients.client_id'], ),
    sa.ForeignKeyConstraint(['user_id'], ['users.id'], ),
    sa.PrimaryKeyConstraint('id')
    )
    ### end Alembic commands ###

def downgrade():
    ### commands auto generated by Alembic - please adjust! ###
    op.drop_table('grants')
    op.drop_table('tokens')
    op.drop_table('oauth_clients')
    ### end Alembic commands ###


"""Pyslabs builtin-data slab manipulation module

"""

import os, io, pickle, itertools

from pyslabs.error import PE_Stabif_Typemismatch
from pyslabs.util import ScalarList, DEBUG_LEVEL, DEBUG_INFO

def length(slab, axis=0):

    return len(slab)

def slice2type(_slice, _type):

    return _type(_slice)

def shape(slab):

    s = []

    while slab:
        try:
            l = len(slab)

            if l > 0:
                s.append(l)
                slab = slab[0]

            else:
                break
        except TypeError:
            break

    return tuple(s)

def dump(path, slab):

    with io.open(path, "wb") as fp:
        pickle.dump(slab, fp)
        fp.flush()
        os.fsync(fp.fileno())

def load(tar_file):

    return pickle.load(tar_file)

def stack(stacker, lower):

    if stacker is None:
        try:
            return type(lower)([lower])

        except TypeError:
            return (lower,)

    if isinstance(stacker, list):
        stacker.append(lower)

    elif isinstance(stacker, tuple):
        stacker += (lower,)

    else:
        import pdb; pdb.set_trace()

    return stacker

def expand_dim(array):

    return type(array)([array])

def get_blank():
    return tuple()

def concatenate(concater, panel, axis):

    if DEBUG_LEVEL > DEBUG_INFO:
        print("Concatenate IN (concat, panel, axis): ", concater, panel, axis)

    from pyslabs import slabif

    if concater is None:
        return panel

    if type(concater) != type(panel) and not isinstance(concater, ScalarList):
        raise PE_Stabif_Typemismatch("%s != %s" % (type(concater).__name__,
                                    type(panel).__name__))

    if isinstance(concater, ScalarList):
        concater.concat(panel)

    elif isinstance(concater, list):
        if axis > 0:
            if len(concater) != len(panel):
                raise PE_Stabif_Lengthmismatch("%d != %d" % (len(concater),
                                        len(panel)))
            buf = []
            for idx in range(len(concater)):
                buf.append(slabif.concatenate(concater[idx], panel[idx], axis=axis-1))
            concater = buf

        else:
            concater.extend(panel)

    elif isinstance(concater, tuple):
        if axis > 0:
            if len(concater) != len(panel):
                raise PE_Stabif_Lengthmismatch("%d != %d" % (len(concater),
                                        len(panel)))
            buf = []
            for idx in range(len(concater)):
                buf.append(slabif.concatenate(concater[idx], panel[idx], axis=axis-1))
            concater = tuple(buf)

        else:
            concater += panel

    else:
        if axis > 0:
            raise PE_Stabif_Wrongaxis()

        concater = ScalarList((concater, panel))

    if DEBUG_LEVEL > DEBUG_INFO:
        print("Concatenate OUT: ", concater)
    return concater

def squeeze(array):
    if DEBUG_LEVEL > DEBUG_INFO:
        print("Squeeze IN: ", array)

    is_squeezed = False

    if isinstance(array, (list, tuple, ScalarList)):
        if len(array) == 1:
            array = array[0]
            is_squeezed = True

    else:
        import pdb; pdb.set_trace()

    if DEBUG_LEVEL > DEBUG_INFO:
        print("Squeeze OUT(array, is_squeezed): ", array, is_squeezed)

    return is_squeezed, array

def get_slice(slab, key):

    from pyslabs import slabif

    if not key:
        return slab

    if isinstance(key, (int, slice)):
        key = (key,)

    if isinstance(key[0], int):
        is_slice = False
        start, stop, step = key[0], key[0]+1, 1

    elif isinstance(key[0], slice):
        is_slice = True
        start, stop, step = key[0].start, key[0].stop, key[0].step

    buf = []

    for item in itertools.islice(slab, start, stop, step):
        if len(key) > 1:
            item_slice = slabif.get_slice(item, key[1:])
            buf.append(item_slice)
        else:
            buf.append(item)

    if not is_slice:
        return buf[0]

    else:
        return slice2type(buf, type(slab))


import bonobo
import pandas as pd
import datetime as dt
import random as rd
import time
import os
from os import listdir
import glob
import requests
import zipfile
import pathlib
import sys

# connection to Data Base
sys.path.append("../conf")
from db_conn import engine

# get relative data folder
PATH = pathlib.Path(__file__).parent.resolve()

YEAR=2019
DIR_PATH = os.getcwd()

def get_stock_list():

    df=pd.read_excel(str(PATH.joinpath("./securities_data.xlsx")),converters={'SBIF_ID':str})
    ruts=(df[df.TIPO == "BANCO"]["RUTSD"]).to_list()
    sbif_ids=(df[df.TIPO == "BANCO"]["SBIF_ID"]).to_list()

    banks=zip(ruts,sbif_ids)

    yield from banks

def extract(*args):
    """
    get list of excel files
    """
    bank_rut= args[0]
    bank_id= args[1]

    while True:
        try:
            print("Downloading file for..." + str(args[0]),end="\n")
            myfile = requests.get("https://www.sbif.cl/sbifweb/internet/bancos/balances/"+str(YEAR)+"/"+bank_id+".zip", allow_redirects=True)
            time.sleep(rd.randint(4,7))
            break
        except:
            print("request failed")
            pass

    open(str(PATH.joinpath("./data_banks/"+bank_id+".zip")), 'wb').write(myfile.content)
    time.sleep(rd.randint(1,2))

    yield (bank_rut,bank_id)

def process(*args):
    """
    Processing excel data
    """
    bank_rut= args[0]
    bank_id= args[1]

    print("Unzipping file for..."+str(bank_rut),end="\n")
    with zipfile.ZipFile(str(PATH.joinpath('./data_banks/'+bank_id+'.zip')), 'r') as zip_ref:
        zip_ref.extractall(str(PATH.joinpath('./data_banks/')))
    time.sleep(rd.randint(2,5))

    print("Processing File for..." + str(bank_rut),end="\n")

    df=pd.read_excel(str(PATH.joinpath('./data_banks/'+bank_id+'.xlsx')),skiprows=3,sheet_name="Resultados")
    df=df[df.columns[4:]]

    df.set_index("Descripción",inplace=True)
    df.index.name="fecha"

    df=df.T[["TOTAL INGRESOS OPERACIONALES","UTILIDAD (PERDIDA) CONSOLIDADA DEL EJERCICIO"]]*1000000
    df=df.reset_index()

    # rename columns
    df.columns=["fecha","ingreso","ganancia"]

    # add variables and transform
    df["moneda"]="PESOS"
    df["fecha_inicio"] = pd.to_datetime(df["fecha"].apply(lambda x: dt.date(x.year,1,1)))
    df["fecha_termino"] = df['fecha']
    df["rut"] = bank_rut

    yield (df, bank_rut)

def load(*args):
    """
    Save dataframe to DB

    Args:
        1: DataFrame - Data from yahoo finance
        2: String - Yahoo IDs
    """

    #args[0].to_csv(str(PATH.joinpath('./data/{}.csv'.format(args[1]))),index=False)

    try: # it will fail if duplicates
        args[0].to_sql('cmf', con=engine, if_exists='append', index=False)
    except:
        pass

def get_graph(**options):
    """
    This function builds the graph that needs to be executed.

    :return: bonobo.Graph

    """
    graph = bonobo.Graph()
    graph.add_chain(get_stock_list,extract, process, load)

    return graph

def get_services(**options):
    """
    This function builds the services dictionary, which is a simple dict of names-to-implementation used by bonobo
    for runtime injection.

    It will be used on top of the defaults provided by bonobo (fs, http, ...). You can override those defaults, or just
    let the framework define them. You can also define your own services and naming is up to you.

    :return: dict
    """
    return {}

# The __main__ block actually execute the graph.
if __name__ == '__main__':

    test = str(PATH.joinpath("./data_banks/*"))
    r = glob.glob(test)
    for i in r:
        os.remove(i)

    test = str(PATH.joinpath("./data/*"))
    r = glob.glob(test)
    for i in r:
        os.remove(i)

    parser = bonobo.get_argument_parser()
    with bonobo.parse_args(parser) as options:
        bonobo.run(
            get_graph(**options),
            services=get_services(**options)
        )


import importlib

import pytest
from pytest_mock import MockerFixture

import src.week02.scripts.build
import src.week02.scripts.collect_gift
import src.week02.scripts.make_gift
import src.week02.scripts.send
from src.utils.mock import MockChainContext, MockUser
from src.utils.mock_scripts import mock_context, run_script

@pytest.fixture(scope="module", autouse=True)
def test_build():
    src.week02.scripts.build.main()

def test_send(mocker: MockerFixture):
    context = MockChainContext()
    u1 = MockUser(context)
    u1.fund(10_000_000)
    u2 = MockUser(context)
    users = {"u1": u1, "u2": u2}
    mock = mock_context(mocker, "src.week02.scripts.send", context, users)

    run_script(
        mocker, src.week02.scripts.send, args=["u1", "u2", "--amount", "5000000"]
    )

    mock.assert_called_once()
    assert u1.balance().coin <= 5000000
    assert u2.balance().coin == 5000000

@pytest.mark.parametrize(
    "script", ["burn", "custom_types", "fourty_two", "fourty_two_typed", "gift"]
)
def test_gift(mocker: MockerFixture, script: str):
    # setup chain
    validator = importlib.import_module(f"src.week02.lecture.{script}").validator
    context = MockChainContext(default_validator=validator)
    u1 = MockUser(context)
    u1.fund(10_000_000)
    u2 = MockUser(context)
    u2.fund(5_000_000)  # add collateral
    users = {"u1": u1, "u2": u2}
    # test make_gift.py
    mock = mock_context(mocker, "src.week02.scripts.make_gift", context, users)
    run_script(
        mocker,
        src.week02.scripts.make_gift,
        args=["u1", "--amount", "5000000", "--script", script],
    )
    mock.assert_called_once()
    # test collect_gift.py
    mock = mock_context(mocker, "src.week02.scripts.collect_gift", context, users)
    try:
        run_script(
            mocker, src.week02.scripts.collect_gift, args=["u2", "--script", script]
        )
        validates = True
    except (AssertionError, ValueError) as e:
        if script != "burn":
            raise e
        validates = False

    mock.assert_called_once()
    assert validates == (script != "burn")
    if script == "burn":
        return

    assert 4_000_000 <= u1.balance().coin <= 5_000_000
    assert 9_000_000 <= u2.balance().coin <= 10_000_000


from django import forms
from .models import Post, Group, Comment

class PostForm(forms.ModelForm):
    text = forms.CharField(
        widget=forms.Textarea,
        label="Текст",
        required=True
    )
    group = forms.ModelChoiceField(
        queryset=Group.objects.all(),
        required=False,
        label="Группа",
    )

    class Meta:
        model = Post
        fields = ("text", "group", "image")

    def clean_text(self):
        data = self.cleaned_data['text']
        if data.replace(" ", "") == "":
            raise forms.ValidationError('Это поле должно быть заполнено.')
        return data

class CommentForm(forms.ModelForm):
    class Meta:
        model = Comment
        fields = ("text",)


#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Created on Sat Jan 22 00:19:11 2022

@author: cycrus
"""

import numpy as np
import pygame
import vector_tools as vec
from helper_functions import make_noise
import copy
import math
import random

TYPE_FOOD = 0
TYPE_WALL = 1
TYPE_ORGANISM = 2
TYPE_ENVIRONMENT = 3

PROP_EDIBLE = 0
PROP_SOLID = 1
PROP_INVISIBLE = 2
PROP_LIVING = 3
PROP_FRUIT = 4
PROP_MEAT = 5
PROP_HOME = 6
PROP_CARRIABLE = 7
PROP_IS_CARRIED = 8

SHADOW_STRENGTH = 100

NOISE_RADIUS = 100

class Entity(object):
    def __init__(self, pos, height, topdown_sprite, texture_sprite, proj_sprite_dims, obj_type, property_list):
        self.pos = pos
        self.prev_pos = self.pos
        self.width = 0
        self.z_pos = 0
        self.base_height = height
        self.height = self.base_height
        self.sides = np.zeros(4)
        self.base_sprite = pygame.image.load(topdown_sprite)
        self.base_proj_sprite = pygame.image.load(texture_sprite)
        self.proj_sprite_dims = proj_sprite_dims
        self.sprite = self.base_sprite
        self.proj_sprite = pygame.Surface(self.proj_sprite_dims,
                                          flags=pygame.SRCALPHA)
        self.proj_sprite.blit(self.base_proj_sprite, (0, 0),
                              (0, 0, self.proj_sprite_dims[0], self.proj_sprite_dims[1]))
        self.proj_shadow = pygame.Surface((self.proj_sprite_dims[1], 10),
                                          flags=pygame.SRCALPHA)
        pygame.draw.ellipse(self.proj_shadow, (0, 0, 0, SHADOW_STRENGTH),
                            (0, 0, self.proj_sprite_dims[1], 6))

        self.size = np.array(self.sprite.get_size())
        self.proj_sprite_size = self.base_proj_sprite.get_size()[1]
        self.type = obj_type
        self.properties = property_list
        self.direction = np.array([0, -1])
        self.calc_sides()
        self.calc_proj_sprite_width()
        self.prev_sides = copy.copy(self.sides)
        self.save_prev_state()

    def exist(self, world):
        pass

    def calc_proj_sprite_width(self):
         self.width = self.proj_sprite_dims[0] / self.proj_sprite_dims[1] * self.height

    def calc_sides(self):
        self.sides[0] = self.pos[0] - self.size[0] / 2
        self.sides[1] = self.pos[1] - self.size[1] / 2
        self.sides[2] = self.pos[0] + self.size[0] / 2
        self.sides[3] = self.pos[1] + self.size[1] / 2

    def save_prev_state(self):
        self.prev_pos = self.pos
        self.prev_size = self.size
        self.prev_sides = copy.copy(self.sides)

    def change_position(self, delta, axis=None):
        if axis is None:
            self.pos = self.pos + delta
        elif axis == 0 or axis == 1:
            self.pos[axis] = self.pos[axis] + delta
        else:
            print("[WARNING] Wrong axis given to Entity.change_position.")
        self.calc_sides()

class Tree(Entity):
    def __init__(self, pos, makes_fruit=True):
        super().__init__(pos, 40, "img/tree.png", "img/tree_proj.png",
                         (40, 40), TYPE_ENVIRONMENT, [PROP_SOLID])
        self.makes_fruit = makes_fruit
        self.spawn_interval = 0
        self.spawn_timer = 0
        self.food_size = np.array([12, 12])
        spawn_distance = self.size * 0.75
        self.spawn_areas = np.array([[self.pos[0]-spawn_distance[0], self.pos[1]],
                                     [self.pos[0], self.pos[1]-spawn_distance[1]],
                                     [self.pos[0]+spawn_distance[0], self.pos[1]],
                                     [self.pos[0], self.pos[1]+spawn_distance[1]]])
        self.checked_blocked_areas = False

        if self.makes_fruit:
            self.spawn_interval = 30 * 60

    def check_spawn_areas(self, wall_list):
        if not self.checked_blocked_areas:
            deleted_areas = []
            for idx, spawn_area in enumerate(self.spawn_areas):
                for wall in wall_list:
                    is_occupied = vec.basic_collision(spawn_area, self.food_size,
                                                      wall.pos, wall.size)
                    if is_occupied:
                        deleted_areas.append(idx)
                        break

            for del_area in reversed(deleted_areas):
                np.delete(self.spawn_areas, del_area)

            self.checked_blocked_areas = True

    def spawn_fruit(self, entity_list):
        if self.spawn_interval > 0 and self.spawn_areas.shape[0] > 0:
            if self.spawn_timer >= self.spawn_interval:
                direction = random.randint(0, self.spawn_areas.shape[0]-1)
                spawn_area = self.spawn_areas[direction]

                is_occupied = False
                for entity in entity_list:
                    if entity is not self:
                        if PROP_EDIBLE in entity.properties or PROP_SOLID in entity.properties:
                            is_occupied = vec.basic_collision(spawn_area, self.food_size,
                                                              entity.pos, entity.size)
                            if is_occupied:
                                break

                if not is_occupied:
                    new_food = Food(spawn_area, PROP_FRUIT)
                    entity_list.append(new_food)

                self.spawn_timer = 0

            self.spawn_timer = self.spawn_timer + 1

    def exist(self, world):
        if self.makes_fruit:
            self.check_spawn_areas(world.walls)
            self.spawn_fruit(world.entities)

class Cave(Entity):
    def __init__(self, pos, inhabitant=None, waketime=0, bedtime=100):
        super().__init__(pos, 40, "img/cave_top.png", "img/cave_proj.png",
                         (40, 40), TYPE_ENVIRONMENT,  [PROP_HOME, PROP_SOLID])
        self.direction = np.array([0, 1])
        self.inhabitant = inhabitant
        self.spawn_pos = self.pos + self.direction * self.size[0]
        if self.inhabitant is not None:
            self.inhabitant.pos = self.spawn_pos
            self.inhabitant.home_cave = self
            temp_angle = vec.get_vector_rotation(self.direction)
            temp_angle = temp_angle * 180/math.pi - 90
            self.inhabitant.init_rotation(temp_angle)
            self.inhabitant.perform_rotation()
        self.waketime = waketime
        self.bedtime = bedtime
        self.is_awake = False
        self.is_dead = False

    def wake_up(self, time, organism_list):
        if not self.is_awake:
            organism_list.append(copy.copy(self.inhabitant))
            self.is_awake = True

    def go_to_sleep(self, time, organism_list):
        if self.is_awake:
            for organism in organism_list:
                if organism.home_cave == self:
                    is_at_home = vec.basic_collision(organism.pos, organism.size, self.spawn_pos, organism.size)
                    if is_at_home:
                        organism_list.remove(organism)
                        self.is_awake = False

    def exist(self, world):
        if self.inhabitant is not None and not self.is_dead:
            waketime_active = False
            if self.waketime < self.bedtime:
                waketime_active = world.time > self.waketime and world.time < self.bedtime
            else:
                waketime_active = world.time > self.waketime or world.time < self.bedtime

            if waketime_active:
                self.wake_up(world.time, world.organisms)
            else:
                self.go_to_sleep(world.time, world.organisms)

class Food(Entity):
    def __init__(self, pos, food_type=PROP_FRUIT):
        if food_type == PROP_FRUIT:
            top_sprite = "img/food_fruit.png"
            proj_sprite = "img/food_fruit_proj_sprite.png"
        elif food_type == PROP_MEAT:
            top_sprite = "img/food_meat.png"
            proj_sprite = "img/food_meat_proj_sprite.png"

        super().__init__(pos, 4, top_sprite, proj_sprite, (40,40), TYPE_FOOD, [PROP_EDIBLE, PROP_CARRIABLE, food_type])

        if food_type == PROP_FRUIT:
            self.max_portions = 3
        elif food_type == PROP_MEAT:
            self.max_portions = 2

        self.portions = self.max_portions
        self.portion_energy = 50
        self.z_pos = 20

        self.calc_sides()
        self.change_image_size()

    def exist(self, world):
        pass
        #make_noise(self.pos, 300, 3, 0.6, world)

    def change_image_size(self):
        self.sprite = pygame.transform.scale(self.base_sprite, (self.base_sprite.get_width() * self.portions,
                                                                self.base_sprite.get_height() * self.portions))
        self.size = np.array(self.sprite.get_size())
        self.proj_sprite_size = self.base_proj_sprite.get_size()[1] * self.portions
        self.height = self.base_height * self.portions
        self.calc_proj_sprite_width()

    def shrink(self):
        if self.portions > 0:
            self.portions = self.portions - 1
            self.change_image_size()

    def grow(self):
        if self.portions < self.max_portions:
            self.portions = self.portions + 1
            self.change_image_size()

class Rock(Entity):
    def __init__(self, pos):
        super().__init__(pos, 30, "img/rock.png", "img/rock_proj_sprite.png",
                         (40, 40), TYPE_ENVIRONMENT, [PROP_SOLID, PROP_CARRIABLE])

class Wall(Entity):
    def __init__(self, pos, symbol, color):
        if symbol == 1:
            sprite_file = "img/grey_wall.png"
        elif symbol == 2:
            sprite_file = "img/green_wall.png"

        super().__init__(pos, 40, sprite_file, "img/wood_wall_texture.png", (40,40), TYPE_WALL, [PROP_SOLID])
        self.calc_sides()


import xml.etree.ElementTree as ET
import pprint

def count_tags(filename):
    tags = {}
    for event, elem in ET.iterparse(filename):
        if elem.tag not in tags.keys():
            tags[elem.tag] = 1
        else:
            tags[elem.tag] += 1
    return tags

def test():

    tags = count_tags('shenzhen_china.osm')
    pprint.pprint(tags)

if __name__ == "__main__":
    test()


import json
with open('in.json', 'r') as x:
    file = json.load(x)
out = []
for task in file:
    userId = task['userId']
    completed = task['completed']
    selectedUser = None
    for user in out:
        if user['userId'] == userId:
            selectedUser = user
            break
    if selectedUser is None:
        selectedUser = {'userId': userId, 'task_completed': 0}
        out.append(selectedUser)
    if completed:
        selectedUser['task_completed'] += 1
with open('out.json', 'w') as x:
    x.write(json.dumps(out, indent=2))


# Import librairies
import cv2 # opencv-python

path='test.png'
def main():
    #Read/load image
    img_bgr=cv2.imread(path)
    img_rgb=cv2.cvtColor(img_bgr,cv2.COLOR_BGR2RGB)
    img_gray=cv2.cvtColor(img_bgr,cv2.COLOR_BGR2GRAY)
    cv2.imshow('BGR',img_bgr)
    cv2.imshow('RGB',img_rgb)
    cv2.imshow('GRAY',img_gray)
    #print(img_gray)
    cv2.waitKey(0) # Lorsque je clique sur 0 je quite la fenetre
    print('Image deplayed!')
if __name__=="__main__":
    main()


from typing import List
from typing import Dict

class Garden:
    def __init__(self, diagram: str, students: List[str] = None):
        self.DEFAULT_STUDENTS: List[str] = [
            'Alice',
            'Bob',
            'Charlie',
            'David',
            'Eve',
            'Fred',
            'Ginny',
            'Harriet',
            'Ileana',
            'Joseph',
            'Kincaid',
            'Larry',
        ]
        self.students = sorted(students or self.DEFAULT_STUDENTS)
        self.diagram: List[str] = diagram.split('\n')
        self.columns: int = len(self.diagram[0])/2
        self.plant_codes: Dict[str, str] = {
            'V': 'Violets',
            'C': 'Clover',
            'R': 'Radishes',
            'G': 'Grass',
        }
        self.student_index = {c: i for i, c in enumerate(self.students)}

    def plants(self, student: str) -> List[str]:
        # Let the KeyError thrown, denote invalid input - no such student
        index = self.student_index[student]
        if self.columns < index:
            raise ValueError(student + " has no cup in the garden")
        index *= 2
        return [self.plant_codes[code] for row in self.diagram
                for code in row[index:index+2]]


import os

from gym import error, spaces
from gym.utils import seeding
import numpy as np
from os import path
import gym

try:
    import mujoco_py
except ImportError as e:
    raise error.DependencyNotInstalled("{}. (HINT: you need to install mujoco_py, and also perform the setup instructions here: https://github.com/openai/mujoco-py/.)".format(e))

DEFAULT_SIZE = 500

class MujocoEnv(gym.Env):
    """
    This is a simplified version of the gym MujocoEnv class.

    Some differences are:
     - Do not automatically set the observation/action space.
    """
    def __init__(self, model_path, frame_skip, device_id=-1, automatically_set_spaces=False):
        if model_path.startswith("/"):
            fullpath = model_path
        else:
            fullpath = os.path.join(os.path.dirname(__file__), "assets", model_path)
        if not path.exists(fullpath):
            raise IOError("File %s does not exist" % fullpath)
        self.frame_skip = frame_skip
        self.model = mujoco_py.load_model_from_path(fullpath)
        self.sim = mujoco_py.MjSim(self.model)
        self.data = self.sim.data
        self.viewer = None
        self._viewers = {}

        self.metadata = {
            'render.modes': ['human', 'rgb_array'],
            'video.frames_per_second': int(np.round(1.0 / self.dt))
        }
        if device_id == -1 and 'gpu_id' in os.environ:
            device_id =int(os.environ['gpu_id'])
        self.device_id = device_id
        self.init_qpos = self.sim.data.qpos.ravel().copy()
        self.init_qvel = self.sim.data.qvel.ravel().copy()
        if automatically_set_spaces:
            observation, _reward, done, _info = self.step(np.zeros(self.model.nu))
            assert not done
            self.obs_dim = observation.size

            bounds = self.model.actuator_ctrlrange.copy()
            low = bounds[:, 0]
            high = bounds[:, 1]
            self.action_space = spaces.Box(low=low, high=high)

            high = np.inf*np.ones(self.obs_dim)
            low = -high
            self.observation_space = spaces.Box(low, high)

        self.seed()

    def seed(self, seed=None):
        self.np_random, seed = seeding.np_random(seed)
        return [seed]

    # methods to override:
    # ----------------------------

    def reset_model(self):
        """
        Reset the robot degrees of freedom (qpos and qvel).
        Implement this in each subclass.
        """
        raise NotImplementedError

    def viewer_setup(self):
        """
        This method is called when the viewer is initialized and after every reset
        Optionally implement this method, if you need to tinker with camera position
        and so forth.
        """
        pass

    # -----------------------------

    def reset(self):
        self.sim.reset()
        ob = self.reset_model()
        if self.viewer is not None:
            self.viewer_setup()
        return ob

    def set_state(self, qpos, qvel):
        assert qpos.shape == (self.model.nq,) and qvel.shape == (self.model.nv,)
        old_state = self.sim.get_state()
        new_state = mujoco_py.MjSimState(old_state.time, qpos, qvel,
                                         old_state.act, old_state.udd_state)
        self.sim.set_state(new_state)
        self.sim.forward()

    @property
    def dt(self):
        return self.model.opt.timestep * self.frame_skip

    def do_simulation(self, ctrl, n_frames=None):
        if n_frames is None:
            n_frames = self.frame_skip
        if self.sim.data.ctrl is not None and ctrl is not None:
            self.sim.data.ctrl[:] = ctrl
        for _ in range(n_frames):
            self.sim.step()

    def render(self, mode='human', width=DEFAULT_SIZE, height=DEFAULT_SIZE):

        if mode == 'rgb_array':
            self._get_viewer(mode).render(width, height)
            data = self._get_viewer(mode).read_pixels(width, height, depth=False)
            # original image is upside-down, so flip it
            return data[::-1, :, :]
        elif mode == 'depth_array':
            self._get_viewer(mode).render(width, height)
            # window size used for old mujoco-py:
            # Extract depth part of the read_pixels() tuple
            data = self._get_viewer(mode).read_pixels(width, height, depth=True)[1]
            # original image is upside-down, so flip it
            return data[::-1, :]
        elif mode == 'human':
            self._get_viewer(mode).render()

    def close(self):
        if self.viewer is not None:
            # self.viewer.finish()
            self.viewer = None
            self._viewers = {}

    def _get_viewer(self, mode):
        self.viewer = self._viewers.get(mode)
        if self.viewer is None:
            if mode == 'human':
                self.viewer = mujoco_py.MjViewer(self.sim)
            elif mode == 'rgb_array' or mode == 'depth_array':
                self.viewer = mujoco_py.MjRenderContextOffscreen(self.sim, -1)

            self.viewer_setup()
            self._viewers[mode] = self.viewer
        return self.viewer

    def get_body_com(self, body_name):
        return self.data.get_body_xpos(body_name)

    def state_vector(self):
        return np.concatenate([
            self.sim.data.qpos.flat,
            self.sim.data.qvel.flat
        ])

    def get_image(self, width=84, height=84, camera_name=None):
        return self.sim.render(
            width=width,
            height=height,
            camera_name=camera_name,
        )

    def initialize_camera(self, init_fctn, mode='rgb_array'):
        sim = self.sim
        viewer = mujoco_py.MjRenderContextOffscreen(sim, device_id=self.device_id)
        # viewer = mujoco_py.MjViewer(sim)
        init_fctn(viewer.cam)
        sim.add_render_context(viewer)


import discord
import os
import requests
import json
import random
from replit import db

client = discord.Client()

sad_words = ["sad","depressed","unhappy","angry","miserable","depressing","failed","failure","fail","loose","lost"]

starter_encouragements = [
  "cheer up !",
  "hang in there !",
  "every day is a blessing",
  "welcome today you are gonna be happy",
  "you are a great person",
  "you are capable more than you think you are"
]
def get_quote():
  response = requests.get("https://zenquotes.io/api/random")
  json_data = json.loads(response.text)
  quote = json_data[0]['q'] + "  _" + json_data[0]['a']
  return(quote)

def update_encouragements(encouraging_message):
  if "encuragements" is db.key():
    encouragements = db["encouragements"]
    encouragements.append(encouraging )

@client.event
async def on_ready():
  print('we have logged in as {0.user}'.format(client))

  @client.event
  async def on_message(message):
    if message.author == client:
      return

    msg = message.content

    if message.content.startswith('$hello'):
      await message.channel.send('hello !')

    if message.content.startswith('$inspire'):
      quote = get_quote()
      await message.channel.send(quote)

    if any(word in msg for word in sad_words):
      await message.channel.send(random.choice(starter_encouragements))

client.run(os.getenv('TOKEN'))


import copy
import importlib
import numpy as np
import os

from statestream.processes.process import STProcess
from statestream.utils.helper import is_scalar_shape

class ProcessSysClient(STProcess):
    """This is generic API for parallel clients synchronized with the core.

    In contrast to core clients, system clients run in a separate process
    instead inside the core. As np/sp/plast/if processes they respect the
    reading / writing phases triggered by the core and may have own
    parameters / variables.
    They may however not write parameters from other processes (e.g. nps)
    due to interference with plasts that might write to them.
    """
    def __init__(self, name, ident, metanet, param, client_param):
        STProcess.__init__(self, name, ident, metanet, param)
        self.type = client_param['type']
        # For system clients we also have to set the client dict.
        self.p = copy.copy(client_param)

    def initialize(self):
        """System client dependent initialization.
        """
        # Initialize system client dependent on its type.
        SysClient = getattr(importlib.import_module("statestream.system_clients." + self.type), self.type)
        self.sys_client = SysClient(self.name, self.net, self.p)

        # Set client side structure for parameters and variables.
        self.sys_client.dat['parameter'] = {}
        self.sys_client.dat['variables'] = {}
        for T in self.sys_client.dat:
            if T in self.p:
                for p,P in self.p[T].items():
                    self.sys_client.dat[T][p] = np.zeros(P['shape'])

        # Call client dependent initialization.
        self.sys_client.initialize(self.shm)

        # Get / set nps, sps.
        if hasattr(self.sys_client, 'nps'):
            self.nps = self.sys_client.nps
        else:
            self.nps = {}
        if hasattr(self.sys_client, 'sps'):
            self.sps = self.sys_client.sps
        else:
            self.nps = {}

        self.shm.update_sys_client()

    def update_frame_readin(self):
        """System client dependent read update.
        """
        if int(self.IPC_PROC["pause"][self.id]) == 0 \
                and int(self.frame_cntr) % int(self.IPC_PROC["period"][self.id]) == int(self.IPC_PROC["period offset"][self.id]):
            # Read system client's parameters.
            for p,P in self.p['parameter'].items():
                self.sys_client.dat['parameter'][p] = np.copy(self.shm.dat[self.p['name']]['parameter'][p])

            # Read necessary (all in-comming) np states / parameters.
            for n in self.nps:
                #self.nps[n].state[0].set_value(np.ascontiguousarray(self.shm.dat[n]["state"]))
                self.nps[n].state[0].set_value(np.require(self.shm.dat[n]["state"],
                                                          requirements='C')[0:self.sys_client.samples,:,:,:])
                if n == self.name:
                    for par in self.shm.dat[n]["parameter"]:
                        if is_scalar_shape(self.shm.layout[n]["parameter"][par].shape):
                            self.nps[n].dat["parameter"][par].set_value(self.shm.dat[n]["parameter"][par][0])
                        else:
                            self.nps[n].dat["parameter"][par].set_value(self.shm.dat[n]["parameter"][par])
            # Read necessary (all in-comming) sp parameters.
            for s in self.sps:
                if self.IPC_PROC["pause"][self.shm.proc_id[s][0]] == 0:
                    for par in self.shm.dat[s]["parameter"]:
                        # Check for parameter sharing.
                        source_sp = s
                        source_par = par
                        if "share params" in self.net["synapse_pools"][s]:
                            if par in self.net["synapse_pools"][s]["share params"]:
                                source_sp = self.net["synapse_pools"][s]["share params"][par][0]
                                source_par = self.net["synapse_pools"][s]["share params"][par][1]
                        if is_scalar_shape(self.shm.layout[s]["parameter"][par].shape):
                            self.sps[s].dat["parameter"][par].set_value(self.shm.dat[source_sp]["parameter"][source_par][0])
                        else:
                            self.sps[s].dat["parameter"][par].set_value(self.shm.dat[source_sp]["parameter"][source_par])
                else:
                    for par in self.shm.dat[s]["parameter"]:
                        if is_scalar_shape(self.shm.layout[s]["parameter"][par].shape):
                            self.sps[s].dat["parameter"][par].set_value(0.0 * self.shm.dat[s]["parameter"][par][0])
                        else:
                            self.sps[s].dat["parameter"][par].set_value(0.0 * self.shm.dat[s]["parameter"][par])

            # Execute system client specific read phase.
            self.sys_client.update_frame_readin(self.shm)

    def update_frame_writeout(self):
        """System client dependent write update.
        """
        # Only execute client if not in pause and if period/offset is met.
        if self.IPC_PROC["pause"][self.id] == 0 and \
                self.frame_cntr % self.IPC_PROC["period"][self.id] == self.IPC_PROC["period offset"][self.id]:
            # Execute write phase.
            self.sys_client.update_frame_writeout()
            # Write variables.
            for v,V in self.p['variables'].items():
                self.shm.set_shm([self.p['name'], 'variables', v], self.sys_client.dat['variables'][v])


import win32gui
from threading import Thread, Lock
import time
import win32process
import psutil
from src.dofus.dofus import Dofus
from src.tools.observer import Observer
import logging
import pyautogui

logger = logging.getLogger(__name__)

class DofusHandler(Thread,Observer):
    """
    Class qui gere les id des fenetres dofus (hwnd) et leur ordre

    event : update_hwnd
    """
    def __init__(self):
        Thread.__init__(self)
        Observer.__init__(self,["update_hwnd","new_select_list","houseevent"])
        self.curr_hwnd = None
        self.running = True
        self.dofus = [Dofus(hwnd) for hwnd in self._get_win()]
        for d in self.dofus:
            d.add_observer("fight",self.update_order)
            d.add_observer("house",self.houseevent)
        self.lock = Lock()
        self.name_order = []
        self.selected = [d for d in self.dofus]

    def houseevent(self):
        self.notify("houseevent")

    def get_hwnds(self):
        return [d.hwnd for d in self.dofus]

    def get_pids(self):
        return [d.pid for d in self.dofus]

    def get_names(self):
        return [d.name for d in self.dofus]

    def get_ports(self):
        return [d.port for d in self.dofus]

    def stop(self):
        self.running = False
        for d in self.dofus:
            d.stop()

    def add_select(self,hwnd):
        d = self.dofus[self.get_index_by_hwnd(hwnd)]
        if(d not in self.selected):
            self.selected.append(d)
        else:
            self.selected.remove(d)
        self.notify("new_select_list",[d.hwnd for d in self.selected])

    def update_order(self,order):
        self.lock.acquire()

        new_order = [self.dofus[self.get_index_by_name(name)] for name in order if name in self.get_names()]
        #ajoute les fenetres qui n'ont pas été ajoutées
        for d in self.dofus:
            if d.hwnd not in [d.hwnd for d in new_order]:
                new_order.append(d)

        self.dofus = new_order
        self.lock.release()
        self.notify("update_hwnd",self.get_hwnds(),self.get_names())

    def _get_win(self):
        tmp = []
        win32gui.EnumWindows(dofusEnumerationHandler, tmp)
        return tmp

    def add_win(self,hwnd):
        self.lock.acquire()
        if hwnd not in self.get_hwnds():
            d = Dofus(hwnd)
            self.dofus.append(d)
            d.add_observer("fight",self.update_order)
            d.add_observer("house",self.houseevent)
            self.selected.append(d)
            self.notify("new_select_list",[d.hwnd for d in self.selected])

            self.lock.release()
            logger.info("new dofus window detected")
            self.notify("update_hwnd",self.get_hwnds(),self.get_names())
            return True

        self.lock.release()
        return False

    def is_dofus_window(self,hwnd):
        return hwnd in self.get_hwnds()

    def get_hwnd_by_name(self,name):
        namelist = self.get_names()
        return self.dofus[namelist.index(name)].hwnd

    def get_index_by_hwnd(self,hwnd):
        return self.get_hwnds().index(hwnd)

    def get_index_by_name(self,name):
        namelist = self.get_names()
        return namelist.index(name)

    def get_dofus_by_port(self,port):
        for d in self.dofus:
            d.update_port()
        return self.dofus[self.get_ports().index(port)]

    def get_next_dofus(self):
        curr = self.get_curr_hwnd()
        i = (self.get_index_by_hwnd(curr)+1) % len(self.dofus)
        return self.dofus[i]

    def get_previous_dofus(self):
        curr = self.get_curr_hwnd()
        i = (self.get_index_by_hwnd(curr)-1) % len(self.dofus)
        return self.dofus[i]

    def get_current_dofus(self):
        hwnd = self.get_curr_hwnd()
        if(hwnd is None):
            return None
        return self.dofus[self.get_index_by_hwnd(hwnd)]

    def get_curr_hwnd(self):
        tmp = win32gui.GetForegroundWindow()
        if(self.is_dofus_window(tmp)):
            self.curr_hwnd = tmp
        return self.curr_hwnd

    def __len__(self):
        return len(self.dofus)

    def remove_win(self,hwnd):
        self.lock.acquire()
        logger.info("dofus window removed")
        i = self.get_index_by_hwnd(hwnd)
        d = self.dofus.pop(i)
        self.selected.remove(d)
        self.notify("new_select_list",[d.hwnd for d in self.selected])
        d.stop()
        del d
        self.lock.release()
        self.notify("update_hwnd",self.get_hwnds(),self.get_names())

    def run(self):
        while self.running :
            hwnd_tmp = self._get_win()

            #test si les fenetres ont été fermées
            for hwnd in self.get_hwnds():
                if hwnd not in hwnd_tmp:
                    self.remove_win(hwnd)

            #test si des fenetres ont été ouvertes
            for hwnd in hwnd_tmp:
                self.add_win(hwnd)

            up = False
            for d in self.dofus:
                if(d.update_name()):
                    up = True
                d.update_port()
            if(up):
                logger.info(f"dofus window name updated {self.get_names()}")
                self.notify("update_hwnd",self.get_hwnds(),self.get_names())

            tmp_name_order = self.get_names()
            if(tmp_name_order != self.name_order):
                self.notify("update_hwnd",self.get_hwnds(),self.get_names())
                self.name_order = self.get_names()

            time.sleep(0.3)

        logger.info("dofus window handler stopped")

    def execute(self,cmd,arg):
        logger.info(f"execute cmd : {cmd}, args : {arg}")
        if(cmd == "goto"):
            curr_dof = self.get_current_dofus()
            if(curr_dof):
                curr_dof.do_async_action(Dofus.goto,*arg)
                return "ok"
            else:
                return "no dofus window selected"
        elif(cmd == "stoptravel"):
            curr_dof = self.get_current_dofus()
            if(curr_dof):
                curr_dof.do_async_action(Dofus.stoptravel)
                return "ok"
            else:
                return "no dofus window selected"
        elif(cmd == "gotos"):
            for d in self.selected:
                d.do_async_action(Dofus.goto,*arg)
            return "ok"
        elif(cmd == "stoptravels"):
            for d in self.selected:
                d.do_async_action(Dofus.stoptravel)
            return "ok"
        elif(cmd == "clickcell"):
            curr_dof = self.get_current_dofus()
            if(curr_dof):
                curr_dof.do_async_action(Dofus.click_cell,*arg)
                return f"click on cellid {arg[0]}"
            else:
                return "no dofus window selected"
        elif(cmd == "zaap"):
            curr_dof = self.get_current_dofus()
            if(curr_dof):
                nom = " ".join(arg)
                curr_dof.do_async_action(Dofus.zaap,nom)
                return "ok"
            else:
                return "no dofus window selected"
        elif(cmd == "zaaps"):
            nom = " ".join(arg)
            for d in self.selected:
                d.do_async_action(Dofus.zaap,nom)
            return "ok"
        elif(cmd == "group"):
            curr_dof = self.get_current_dofus()
            if(curr_dof):
                listinv = [n for n in self.get_names() if n != curr_dof.name and n != ""]
                if(len(listinv) == 0):
                    return "no other dofus window"
                curr_dof.do_async_action(Dofus.invite,listinv)
                return f"invite {listinv}"
            else:
                return "no dofus window selected"
        elif(cmd == "reset"):
            curr_dof = self.get_current_dofus()
            if(curr_dof):
                self.remove_win(curr_dof.hwnd)
                return f"{curr_dof.name} reset"
            else:
                return "no dofus window selected"
        elif(cmd == "flagcalibrage"):
            curr_dof = self.get_current_dofus()
            #normalement une chasse doit être lancée sinon t'es con
            if(curr_dof):
                if(curr_dof.chasseObject is not None):
                    pos = pyautogui.locateCenterOnScreen('ressources\\img\\hintflag.png',confidence=0.9)
                    if(pos is not None):
                        x,y = pos
                    else :
                        return "Flag not found\n/!\ attention à ne pas cacher le flag avec la fenêtre de commande"
                    y = y - 30*(len(curr_dof.chasseObject.listindice)-1)
                    for d in self.dofus:
                        if(d.chasseObject is not None):
                            d.chasseObject.set_flag_pos(x,y)
                    return f"Flag on {x},{y}"
                else:
                    return "Une chasse doit être lancée"
            else:
                return "no dofus window selected"

def dofusEnumerationHandler(hwnd, top_windows):
    name = win32gui.GetWindowText(hwnd)
    _,pid = win32process.GetWindowThreadProcessId(hwnd)
    if pid < 0:
        return
    exe = psutil.Process(pid).exe()
    visible = win32gui.IsWindowVisible(hwnd)
    if("dofus 2" in name.lower() and "dofus.exe" in exe.lower() and visible):
        top_windows.append(hwnd)


from flask import render_template, request, abort, json, Response
from settings import app
from googletrans import Translator

@app.route("/")
def index():
    return render_template('index.html',)

@app.route("/translate")
def translate():
    text = request.args.get('text', None)
    lang = request.args.get('lang', 'en')
    if text == '' or text is None:
        return abort(Response(json.dumps({
            'error': 'No text provided'
        }), status=400))
    if lang == '':
        return abort(Response(json.dumps({
            'error': 'No language provided'
        }), status=400))
    try:
        translator = Translator()
        translated = translator.translate(text, dest=lang)
        return {
            'text': translated.text,
        }
    except Exception as e:
        print(e)
        return abort(Response(json.dumps({
            'error': 'Something went wrong',
        }), status=500))


# enable default 1D tester for this module
from opensees.physical_properties.utils.tester.EnableTester1D import *
from opensees.utils.override_utils import get_function_from_module

import PyMpc.Units as u
from PyMpc import *
from mpc_utils_html import *
import opensees.utils.tcl_input as tclin

def makeXObjectMetaData():

	def mka(name, group, descr, atype, adim = None, dval = None):
		a = MpcAttributeMetaData()
		a.type = atype
		a.name = name
		a.group = group
		a.description = (
			html_par(html_begin()) +
			html_par(html_boldtext(name)+'
') +
			html_par(descr) +
			html_par(html_href('https://asdeasoft.net/?stko-support','DamageTC1D')+'
') +
			html_end()
			)
		if adim is not None:
			a.dimension = adim
		if dval is not None:
			a.setDefault(dval)
		return a

	E = mka("E", "Elasticity", "Young's modulus", MpcAttributeType.QuantityScalar, adim=u.F/u.L**2)
	ft = mka("ft", "Tension", "Tensile strength", MpcAttributeType.QuantityScalar, adim=u.F/u.L**2)
	Gt = mka("Gt", "Tension", ("Tensile fracture energy.
"
		"It should be per unit area, and it will be automatically regularized "
		"if the flag autoRegularization is set to True (Default).
"
		"Otherwise it should be input as specific fracture energy (per unit volume)."),
		MpcAttributeType.QuantityScalar, adim=u.F/u.L)
	fc0 = mka("fc0", "Compression", "Compressive elastic limit", MpcAttributeType.QuantityScalar, adim=u.F/u.L**2)
	fcp = mka("fcp", "Compression", "Compressive peak strength", MpcAttributeType.QuantityScalar, adim=u.F/u.L**2)
	fcr = mka("fcr", "Compression", "Compressive residual strength", MpcAttributeType.QuantityScalar, adim=u.F/u.L**2)
	ep = mka("ep", "Compression", "Compressive strain at peak strength", MpcAttributeType.Real)
	Gc = mka("Gc", "Compression", ("Compressive fracture energy.
"
		"It should be per unit area, and it will be automatically regularized "
		"if the flag autoRegularization is set to True (Default).
"
		"Otherwise it should be input as specific fracture energy (per unit volume)."),
		MpcAttributeType.QuantityScalar, adim=u.F/u.L)
	c1  = mka("c1", "Compression", "Compressive law shape parameter", MpcAttributeType.Real, dval=0.65)
	c2  = mka("c2", "Compression", "Compressive law shape parameter", MpcAttributeType.Real, dval=0.50)
	c3  = mka("c3", "Compression", "Compressive law shape parameter", MpcAttributeType.Real, dval=1.50)
	eta  = mka("eta", "Misc", "Viscosity parameter", MpcAttributeType.Real, dval=0.0)
	pdf_t = mka("pdf_t", "Misc", "Plastic-Damage factor for tensile response in range [0 (full damage) ... (mixed) ... 1 (full plasticity)]", MpcAttributeType.Real, dval=0.0)
	pdf_c = mka("pdf_c", "Misc", "Plastic-Damage factor for compressive response in range [0 (full damage) ... (mixed) ... 1 (full plasticity)]", MpcAttributeType.Real, dval=0.7)
	algo = mka("integration", "Misc", ("Inegration type.
"
		"(Default) Implicit: A standard Backward-Euler integration scheme.
"
		"IMPL-EX: A mixed IMPLicit-EXplicit integration scheme. The resulting response is "
		"step-wise linear with a positive-definite tangent stiffnes matrix due to the explicit extrapolation of the internal variables.
"
		"However the time-step should be smaller than the one used for an implicit scheme"),
		MpcAttributeType.String, dval="Implicit")
	algo.sourceType = MpcAttributeSourceType.List
	algo.setSourceList(['Implicit', 'IMPL-EX'])
	implex_check = mka("implexCheckError", "Misc", "Check the IMPL-EX error making sure it is kept under a user-defined tolerance", MpcAttributeType.Boolean, dval=False)
	implex_tol = mka("implexErrorTolerance", "Misc", "The maximum allowed relative IMPL-EX error", MpcAttributeType.Real, dval=0.05)
	implex_red = mka("implexErrorTimeReductionLimit", "Misc", "The pseudo-time-step reduction limit under which the implex error check is not performed", MpcAttributeType.Real, dval=0.01)
	reg = mka("autoRegularization", "Misc", ("When this flag is True (Default), the input fracture energies (Gt and Gc) "
		"will be divided by the element characteristic length, in order to obtain a response which is mesh-size independent.
"
		"If turn this flag Off, the input fracture energies will be used as they are."),
		MpcAttributeType.Boolean, dval=True)
	ctype = mka("constitutiveTensorType", "Misc", ("Constitutive Tensor Tyope.
"
		"(Default) Tangent: The algorithmic tangent tensor.
"
		"TangentPerturbation: The algorithmic tangent tensor computed with numerical differentiation.
"
		"Secant: The secant tensor.
"),
		MpcAttributeType.String, dval="Tangent")
	ctype.sourceType = MpcAttributeSourceType.List
	ctype.setSourceList(['Tangent', 'TangentPerturbation', 'Secant'])

	xom = MpcXObjectMetaData()
	xom.name = 'DamageTC1D'
	xom.Xgroup = 'ASDEASoftware'
	# Elasticity
	xom.addAttribute(E)
	# Tension
	xom.addAttribute(ft)
	xom.addAttribute(Gt)
	# Compression
	xom.addAttribute(fc0)
	xom.addAttribute(fcp)
	xom.addAttribute(fcr)
	xom.addAttribute(ep)
	xom.addAttribute(Gc)
	xom.addAttribute(c1)
	xom.addAttribute(c2)
	xom.addAttribute(c3)
	# Misc
	xom.addAttribute(eta)
	xom.addAttribute(pdf_t)
	xom.addAttribute(pdf_c)
	xom.addAttribute(algo)
	xom.addAttribute(implex_check)
	xom.addAttribute(implex_tol)
	xom.addAttribute(implex_red)
	xom.addAttribute(reg)
	xom.addAttribute(ctype)

	return xom

def _check_implex(xobj):
	is_implex = xobj.getAttribute('integration').string == 'IMPL-EX'
	xobj.getAttribute('implexCheckError').visible = is_implex
	xobj.getAttribute('implexErrorTolerance').visible = is_implex

_onEditBegin = get_function_from_module(__name__, 'onEditBegin')
def onEditBegin(editor, xobj):
	if _onEditBegin: _onEditBegin(editor, xobj)
	_check_implex(xobj)

def onAttributeChanged(editor, xobj, attribute_name):
	if attribute_name == 'integration':
		_check_implex(xobj)

def writeTcl(pinfo):

	xobj = pinfo.phys_prop.XObject
	tag = xobj.parent.componentId

	# utils
	def geta(name):
		at = xobj.getAttribute(name)
		if at is None:
			raise Exception('Error: cannot find "{}" attribute'.format(name))
		return at

	def getCtype(value):
		if value == 'TangentPerturbation':
			return 1
		elif value == 'Secant':
			return 2
		else:
			return 0

	# get parameters
	params = ([
		('E', geta('E').quantityScalar.value),
		('ft', geta('ft').quantityScalar.value),
		('Gt', geta('Gt').quantityScalar.value),
		('fc0', geta('fc0').quantityScalar.value),
		('fcp', geta('fcp').quantityScalar.value),
		('fcr', geta('fcr').quantityScalar.value),
		('ep', geta('ep').real),
		('Gc', geta('Gc').quantityScalar.value),
		('c1', geta('c1').real),
		('c2', geta('c2').real),
		('c3', geta('c3').real),
		('eta', geta('eta').real),
		('pdf_t', geta('pdf_t').real),
		('pdf_c', geta('pdf_c').real),
		('implex', (0 if geta('integration').string == 'Implicit' else 1)),
		('implexCheckError', (1 if geta('implexCheckError').boolean else 0)),
		('implexErrorTolerance', geta('implexErrorTolerance').real),
		('implexErrorTimeReductionLimit', geta('implexErrorTimeReductionLimit').real),
		('autoRegularization', (1 if geta('autoRegularization').boolean else 0)),
		('constitutiveTensorType', getCtype(geta('constitutiveTensorType').string))
	])

	# todo: pre check parameters

	# now write the string into the file
	pinfo.out_file.write(
		'{}uniaxialMaterial plugin {} pdm DamageTC1D {}\n'.format(
			pinfo.indent, tag,
			' '.join( ['-{} {}'.format(item[0], item[1]) for item in params] ))
		)


# Import PyTorch
import torch
from torch import nn
from torch import Tensor
from torch.nn import functional as F
from torch.cuda.amp.autocast_mode import autocast
from torch.nn.modules.activation import MultiheadAttention
# Import custom modules
from .layer import TransformerEncoderLayer

class Transformer(nn.Module):
    def __init__(self, model_type: str = 'sep', input_size: int = 3500,
                 d_model: int = 512, d_embedding: int = 256,
                 n_head: int = 8, dim_feedforward: int = 2048,
                 num_encoder_layer: int = 10, dropout: float = 0.3):

        super(Transformer, self).__init__()

        self.model_type = model_type
        self.dropout = nn.Dropout(dropout)
        if model_type == 'sep':
            n_classes = 1
        elif model_type == 'total':
            n_classes = 2
        else:
            raise NameError(f'{model_type} is not defined')

        # Image embedding part
        self.src_input_linear = nn.Embedding(input_size, d_embedding)
        self.src_input_norm = nn.LayerNorm(d_embedding, eps=1e-12)
        self.src_input_linear2 = nn.Linear(d_embedding, d_model)

        # Transformer Encoder part
        self_attn = MultiheadAttention(d_model, n_head, dropout=dropout)
        self.encoders = nn.ModuleList([
            TransformerEncoderLayer(d_model, self_attn, dim_feedforward, dropout=dropout) \
                for i in range(num_encoder_layer)])

        # Transformer Encoder part 2: Seperate model type (sep)
        self_attn2 = MultiheadAttention(d_model, n_head, dropout=dropout)
        self.encoders2 = nn.ModuleList([
            TransformerEncoderLayer(d_model, self_attn2, dim_feedforward, dropout=dropout) \
                for i in range(num_encoder_layer)])

        # Target linear part (Not averaging)
        self.trg_output_linear = nn.Linear(d_model, d_embedding)
        self.trg_output_norm = nn.LayerNorm(d_embedding, eps=1e-12)
        self.trg_output_linear2 = nn.Linear(d_embedding, n_classes)

        if model_type == 'sep':
            self.trg_output_linear_sep = nn.Linear(d_model, d_embedding)
            self.trg_output_norm_sep = nn.LayerNorm(d_embedding, eps=1e-12)
            self.trg_output_linear2_sep = nn.Linear(d_embedding, n_classes)

        # Initialization
        for p in self.parameters():
            if p.dim() > 1:
                nn.init.kaiming_uniform_(p)

    @autocast()
    def forward(self, src_menu: Tensor) -> Tensor:
        # Image embedding
        emb_out = self.src_input_norm(self.dropout(F.gelu(self.src_input_linear(src_menu))))
        emb_out = self.src_input_linear2(emb_out)
        encoder_out = emb_out.transpose(0, 1)

        # Transformer Encoder
        for encoder in self.encoders:
            encoder_out = encoder(encoder_out)

        # Target linear
        encoder_out = encoder_out.transpose(0, 1)
        encoder_out = self.trg_output_norm(self.dropout(F.gelu(self.trg_output_linear(encoder_out))))
        encoder_out = self.trg_output_linear2(encoder_out)

        # If model_type is 'sep'
        if self.model_type == 'sep':
            encoder_out2 = emb_out.transpose(0, 1)
            for encoder in self.encoders2:
                encoder_out2 = encoder(encoder_out2)

            encoder_out2 = encoder_out2.transpose(0, 1)
            encoder_out2 = self.trg_output_norm_sep(self.dropout(F.gelu(self.trg_output_linear_sep(encoder_out2))))
            encoder_out2 = self.trg_output_linear2_sep(encoder_out2)

        if self.model_type == 'total':
            logit = encoder_out[:,0,:]
        elif self.model_type == 'sep':
            logit = torch.cat([encoder_out[:,0,:], encoder_out2[:,0,:]], dim=1)

        return logit


import json

import pandas as pd
from keras import models
from _logging._logger import get_logger
from datetime import datetime

logger = get_logger(__name__)

class ModelWrapper:
    def __init__(self, name: str, model: models, compiled: bool, trained: bool, history_json: json = None,
                 update_time_stamp=None):
        self.trained = trained
        self.compiled = compiled
        self.model = model
        self.name = name
        self.history_json = history_json
        self.update_time_stamp = update_time_stamp
        self.deleted = False

class Singleton(type):
    _instances = {}

    def __call__(cls, *args, **kwargs):
        if cls not in cls._instances:
            cls._instances[cls] = super(Singleton, cls).__call__(*args, **kwargs)
        return cls._instances[cls]

class KerasWrapper(metaclass=Singleton):

    def __init__(self, _models: dict = None):
        if _models:
            self.models = _models
        else:
            self.models = dict()

    def add_model(self, name: str, model: models, compiled=False, trained=False):
        logger.info(f"Add new Model {name}")
        self.models[name] = ModelWrapper(name=name,
                                         model=model,
                                         compiled=compiled,
                                         trained=trained)
        self.models[name].update_time_stamp = datetime.now()

    def compile(self, model_name: str, optimizer: str, loss: str, metrics: list):
        logger.info(f"Compiled model {model_name}")
        self.get_model(model_name).model.compile(optimizer=optimizer, loss=loss, metrics=metrics)
        self.get_model(model_name).compiled = True
        self.get_model(model_name).update_time_stamp = datetime.now()

    def train(self, model_name: str, train_data, train_labels, val_data, val_labels, epochs: int, batch_size: int):
        logger.info(f"Train model {model_name}")
        history = self.get_model(model_name).model.fit(train_data, train_labels,
                                                       epochs=epochs,
                                                       batch_size=batch_size,
                                                       validation_data=(val_data, val_labels))
        self.get_model(model_name).trained = True
        self.get_model(model_name).history_json = pd.DataFrame.from_dict(history.history).to_json()
        self.get_model(model_name).update_time_stamp = datetime.now()

    def evaluate(self, model_name: str, test_data, test_labels):
        logger.info(f"Evaluate model {model_name}")
        return self.get_model(model_name).model.evaluate(test_data, test_labels)

    def serialize_model(self, model_name: str, path: str):
        self.get_model(model_name).model.save(path)

    def delete_network(self, model_name: str):
        self.get_model(model_name).deleted = True

    def get_models_names(self) -> list:
        if self.models:
            return [model.name for model in list(self.models.values()) if not model.deleted]
        else:
            return []

    def get_models_names_and_statuses(self) -> list:
        if self.models:
            return [{"name": model.name, "compiled": model.compiled, "trained": model.trained} for model in
                    list(self.models.values()) if not model.deleted]
        else:
            return []

    def get_models(self) -> list or None:
        if self.models:
            return [model for model in list(self.models.values()) if not model.deleted]
        else:
            return None

    def get_model(self, model_name: str):
        return self.models[model_name] if not self.models[model_name].deleted else None

    def get_deleted_models_names(self) -> list:
        if self.models:
            return [model.name for model in list(self.models.values()) if model.deleted]
        else:
            return []

    def remove_model(self, name: str):
        del self.models[name]


import torch
import torchvision
import cv2
import numpy as np
import os
from PIL import Image
from matplotlib import pyplot as plt
import argparse
from skimage.transform import resize

# Load the trained model
import model as myModel

ddir = '../Downloads/DeepLabv3-TS/test_files/sg_data/'
root = '../Downloads/DeepLabv3-TS/masked/'
exp_dir = '../Downloads/DeepLabv3-TS/exp_out/'
checkpoint = torch.load(exp_dir + 'trained_weights_all_ep30.pth.tar')

ap = argparse.ArgumentParser()
ap.add_argument("-i", "--image", help = "path to the image file")
ap.add_argument("-c", "--coords",
    help = "comma seperated list of source points")
args = vars(ap.parse_args())

def convex(dir):
    img = cv2.imread(dir)
    img1 = img.copy()
    imgray = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)

    ret, thr = cv2.threshold(imgray,255,0,180)
    contours,_ = cv2.findContours(thr, cv2.RETR_TREE,cv2.CHAIN_APPROX_SIMPLE)

    contours_sizes= [(cv2.contourArea(cnt), cnt) for cnt in contours]
    biggest_contour = max(contours_sizes, key=lambda x: x[0])[1]

    #cnt = contours[0]
    cnt = biggest_contour

    x,y,w,h = cv2.boundingRect(cnt)

    rect = cv2.minAreaRect(cnt)
    box = cv2.boxPoints(rect)
    box = np.int0(box)

    cv2.drawContours(img,[box],0,(0,255,0),1)

    return box

def tl(x,y,w,h):
    x = x**2
    y = y**2
    result = (x+y) **0.5
    return result

def bl(x,y,w,h):
    y = h-y
    x = x**2
    y = y**2
    result = (x+y) **0.5
    return result

def tr(x,y,w,h):
    x = w-x
    x = x**2
    y = y**2
    result = (x+y) **0.5
    return result

def br(x,y,w,h):
    x= w-x
    y= h-y
    x = x**2
    y = y**2
    result = (x+y) **0.5
    return result

def tr_re(x,y,bl_x,bl_y):
    x= bl_x-x
    y= bl_y-y
    x = x**2
    y = y**2
    result = (x+y) **0.5
    return result

def order_points(pts):
	# initialzie a list of coordinates that will be ordered
	# such that the first entry in the list is the top-left,
	# the second entry is the top-right, the third is the
	# bottom-right, and the fourth is the bottom-left
	rect = np.zeros((4, 2), dtype = "float32")

	# the top-left point will have the smallest sum, whereas
	# the bottom-right point will have the largest sum
	s = pts.sum(axis = 1)
	rect[0] = pts[np.argmin(s)]
	rect[2] = pts[np.argmax(s)]

	# now, compute the difference between the points, the
	# top-right point will have the smallest difference,
	# whereas the bottom-left will have the largest difference
	diff = np.diff(pts, axis = 1)
	rect[1] = pts[np.argmin(diff)]
	rect[3] = pts[np.argmax(diff)]

	# return the ordered coordinates
	return rect

def four_point_transform(image, pts):
    	# obtain a consistent order of the points and unpack them
	# individually
	rect = order_points(pts)
	(tl, tr, br, bl) = rect

	# compute the width of the new image, which will be the
	# maximum distance between bottom-right and bottom-left
	# x-coordiates or the top-right and top-left x-coordinates
	widthA = np.sqrt(((br[0] - bl[0]) ** 2) + ((br[1] - bl[1]) ** 2))
	widthB = np.sqrt(((tr[0] - tl[0]) ** 2) + ((tr[1] - tl[1]) ** 2))
	maxWidth = max(int(widthA), int(widthB))

	# compute the height of the new image, which will be the
	# maximum distance between the top-right and bottom-right
	# y-coordinates or the top-left and bottom-left y-coordinates
	heightA = np.sqrt(((tr[0] - br[0]) ** 2) + ((tr[1] - br[1]) ** 2))
	heightB = np.sqrt(((tl[0] - bl[0]) ** 2) + ((tl[1] - bl[1]) ** 2))
	maxHeight = max(int(heightA), int(heightB))

	# now that we have the dimensions of the new image, construct
	# the set of destination points to obtain a "birds eye view",
	# (i.e. top-down view) of the image, again specifying points
	# in the top-left, top-right, bottom-right, and bottom-left
	# order
	dst = np.array([
		[0, 0],
		[maxWidth - 1, 0],
		[maxWidth - 1, maxHeight - 1],
		[0, maxHeight - 1]], dtype = "float32")

	# compute the perspective transform matrix and then apply it
	M = cv2.getPerspectiveTransform(rect, dst)
	warped = cv2.warpPerspective(image, M, (maxWidth, maxHeight))

	# return the warped image
	return warped

preprocess = torchvision.transforms.Compose([
                    torchvision.transforms.ToTensor(),
                    torchvision.transforms.Normalize(mean=[0.485, 0.456, 0.406], std=[0.229, 0.224, 0.225]),
                ])
model = myModel.createDeepLabv3(outputchannels=2) # give nclasses
#model.load_state_dict(torch.load(exp_dir + 'trained_weights.best_acc.pth.tar'))

#checkpoint = torch.load(exp_dir + 'trained_weights_burn_imgs_550size.pth.tar')
model.load_state_dict(checkpoint['model_state_dict'])

#model = torch.load(exp_dir + 'weights.pt')
# Set the model to evaluate mode
model.eval()
#device = torch.device("cuda:0" if torch.cuda.is_available() else "cpu")
device = torch.device('cpu')

# Read  a sample image and mask from the data-set
per_point = [0 for j in range(8)]
flist = os.listdir(ddir)
index_count = [[0 for j in range(2)] for i in range(400000)]
length_cal = [0 for j in range(4)]

for file in flist:
    imfile = ddir + file
    print ('filename: ', file, ' in ', ddir)
    im = np.ascontiguousarray(cv2.imread(imfile)[:,:,::-1])
    print (im.shape)
    #resizing
    re_size = 400
    rows, cols, channels = im.shape
    scale = re_size / float(im.shape[1])
    im = cv2.resize(im,(re_size,int(rows*scale)))
    #end

    print(im.shape)
    intensor = preprocess (im)
    batch = intensor.reshape(1,*intensor.shape)
    print (batch.shape, batch.dtype)

    with torch.no_grad():
        a = model(batch.to(device))
        re = a['out'].argmax(dim=1).data.cpu().numpy()[0]
        #re = cv2.resize(re,(cols,rows))
        #plt.imsave(root+'low/'+file,re)

        #re = resize(re, (rows, cols))

        plt.imsave(root+file,re)

imgs = list(sorted(os.listdir(os.path.join(root))))
#print(imgs)

for filename in imgs :

    print(root + filename)
    img = Image.open(root + filename).convert("RGB")
    (width,height) = img.size
    outputImg = Image.new("RGB", (width,height),(0,0,0))
    output = outputImg.load()

    k=0

    for y in range(0, height):
        for x in range(0, width):
            r, g, b = img.getpixel((x, y))
            if r > 140 :
                output[x,y] = (255,0,0)
            elif b > 140 :
                output[x,y] = (0,0,255)
            elif g > 140 :
                output[x,y] = (0,255,0)
            else :
                output[x,y] = (0,0,0)

    outputImg.save(root + filename)

    rectangle = convex(root+filename)
    # box[0][1~2] br ~ bl ~ tl ~tr

    #up
    for y in range(0,rectangle[2][1]):
        for x in range(0,width):
            output[x,y] = (0,0,0)
    #down
    for y in range(rectangle[0][1],height):
        for x in range(0,width):
            output[x,y] = (0,0,0)
    #left
    for y in range(0,height):
        for x in range(0,rectangle[1][0]):
            output[x,y] = (0,0,0)
    #right
    for y in range(0,height):
        for x in range(rectangle[3][0],width):
            output[x,y] = (0,0,0)
    outputImg = outputImg.convert("RGB")
    outputImg.save(root + filename)

    for y in range(0, height):
        for x in range(0, width):
            r, g, b = outputImg.getpixel((x, y))
            if(r>50):
                index_count[k][0] = x
                index_count[k][1] = y
                k+=1
                #print(k)

    for i in range(0,len(length_cal)):
        length_cal[i] = 3000
    for i in range(1,k):
        if(tl(index_count[i][0],index_count[i][1],width,height)<length_cal[0]):
            per_point[0] = index_count[i][0]
            per_point[1] = index_count[i][1]
            length_cal[0] = tl(index_count[i][0],index_count[i][1],width,height) #tl

        if(bl(index_count[i][0],index_count[i][1],width,height)<length_cal[1]):
            per_point[2] = index_count[i][0]
            per_point[3] = index_count[i][1]
            length_cal[1] = bl(index_count[i][0],index_count[i][1],width,height) #bl

        if(tr(index_count[i][0],index_count[i][1],width,height)<length_cal[2]):
            per_point[4] = index_count[i][0]
            per_point[5] = index_count[i][1]
            length_cal[2] = tr(index_count[i][0],index_count[i][1],width,height) #tr

        if(br(index_count[i][0],index_count[i][1],width,height)<length_cal[3]):
            per_point[6] = index_count[i][0]
            per_point[7] = index_count[i][1]
            length_cal[3] = br(index_count[i][0],index_count[i][1],width,height) #br

    #rotated
    if(per_point[7]-per_point[3]>abs(per_point[3]-per_point[5])/10):
        for i in range(1,k):
            if(index_count[i][1]<index_count[i-1][1]):
                per_point[0] = index_count[i][0]
                per_point[1] = index_count[i][1]
                #print("distort changed!")
        #for i in range(1,k):
            if(index_count[i][0]<index_count[i-1][0]):
            #if(tr_re(index_count[i][0],index_count[i][1],per_point[2],per_point[3])>tr_re(index_count[i-1][0],index_count[i-1][1],per_point[2],per_point[3])):
                per_point[4] = index_count[i][0]
                #per_point[5] = index_count[i][1]
            #length_cal[0] = tl(index_count[i][0],index_count[i][1],width,height) #tl
        #per_point[4] = per_point[6]
    print(per_point)

    expend_pixel = 1
    #tl
    per_point[0] -= expend_pixel #x
    per_point[1] -= expend_pixel #y

    #bl
    per_point[2] -= expend_pixel #x
    per_point[3] += expend_pixel #y

    #tr
    per_point[4] += expend_pixel #x
    per_point[5] -= expend_pixel #y

    #br
    per_point[6] += expend_pixel #x
    per_point[7] += expend_pixel #y

    args["image"] = ddir+filename

    args["coords"] =  "[("+str(per_point[0])+","+str(per_point[1])+"), ("+str(per_point[2])+","+str(per_point[3])+"), ("+str(per_point[4])+", "+str(per_point[5])+"), ("+str(per_point[6])+", "+str(per_point[7])+")]"
    #determine the coordinates without pre-supplying them tl, tr, br, bl
    image = cv2.imread(args["image"])

    rows, cols, channels = image.shape
    scale = re_size / float(image.shape[1])
    image = cv2.resize(image,(re_size,int(rows*scale)))

    pts = np.array(eval(args["coords"]), dtype = "float32")

    warped = four_point_transform(image, pts)
    #cv2.imshow("warped",warped)
    #cv2.waitKey(0)

    cv2.imwrite("../Downloads/DeepLabv3-TS/"+"warped"+filename,warped)
    #cv2.waitKey(0)
    print("warp_saved")


import numpy as np
import argparse, sys, os, time, glob

import pandas as pd

#%% Functions
def load_args():
    ap = argparse.ArgumentParser(
        description='Print train statistics stored on the csv log files.',
        formatter_class=argparse.ArgumentDefaultsHelpFormatter)

    # Positional arguments
    ap.add_argument('summary_dirs',
        help='Directory with the train summary information.',
        nargs='*',
        type=str)

    # Optional arguments
    ap.add_argument('-c','--criteria',
        help="criteria for picking the best epoch",
        choices=['val_acc', 'val_loss'])
    ap.add_argument('-u','--update',
        help="update summary file (overwrite)",
        action='store_true')
    ap.add_argument('-s','--seqs-eval',
        help="evaluation over sequences average (sample 'all')",
        action='store_true')

    ap.add_argument('--print_args',
        help="whether to print current arguments' values",
        action='store_false')
        # action='store_true')

    args = ap.parse_args()

    return args

def read_runs(summary_dir, criteria=None, seqs_eval=False):
    if not seqs_eval: # Central frames only
        summary_filename = '/summary.csv'
        run_filename = '/fit_history.csv'
        log_filename = '/training.log'
    else:
        summary_filename = '/summary-pooled_val_acc.csv'
        run_filename = '/pooled_val_acc.csv'
        log_filename = run_filename

    hist_paths = glob.glob(summary_dir+'/fold_*'+summary_filename)
    hist_paths.sort()

    folds_with_summary = [ hist_path.split('/')[-2] for hist_path in hist_paths ]

    reruns_dirs = glob.glob(summary_dir+'/rerun_*/') + glob.glob(summary_dir+'/fold_*/')
    reruns_dirs.sort()

    reruns_dirs = [ r for r in reruns_dirs
        if not any( fold in r for fold in folds_with_summary) ]

    for rerun_dir in reruns_dirs:
        if 'rerun' in rerun_dir:
            rerun_hist = glob.glob(rerun_dir + run_filename)
            if rerun_hist == []:
                rerun_hist = glob.glob(rerun_dir + log_filename)
                if rerun_hist != []:
                    if os.stat(rerun_hist[0]).st_size != 0: # log is not empty
                        print("WARNING: Training not finished for '{}', using '{}'".format(
                            rerun_dir.split('/')[-2], log_filename))
                    else:
                        rerun_hist = []
        else:
            print("WARNING: Training not finished for '{}', using '{}'".format(
                            rerun_dir.split('/')[-2], log_filename))
            fold_reruns_dirs = glob.glob(rerun_dir+'/rerun_*/')
            fold_reruns_dirs.sort()

            fold_best_epochs = read_runs(rerun_dir, criteria=criteria, seqs_eval=seqs_eval)
            if fold_best_epochs != []:
                fold_df = pd.concat(fold_best_epochs, axis=1, sort=False).T.reset_index(drop=True)
                best_rerun = fold_reruns_dirs[fold_df.val_acc.idxmax()]
                best_hist = glob.glob(best_rerun + run_filename) + glob.glob(best_rerun + log_filename)

                rerun_hist = [ best_hist[0] ]
            else:
                rerun_hist = []
        hist_paths += rerun_hist

    hist_paths.sort()

    best_epochs = []
    for rerun_idx, hist_path in enumerate(hist_paths):
        hist_df = pd.read_csv(hist_path)

        if criteria.endswith('loss'):
            best_epoch = hist_df.loc[hist_df[criteria].idxmin()]
        elif criteria.endswith('acc'):
            if not seqs_eval: # Central frames only
                sorted_hist_df = hist_df.sort_values([criteria, 'val_loss'],
                    ascending=[False, True])
            else:
                sorted_hist_df = hist_df.sort_values([criteria], ascending=[False])
            best_epoch = sorted_hist_df.iloc[0]

        best_epochs.append(best_epoch)

    return best_epochs

def pretty_print_stats(stats_df, short_version=False, seqs_eval=False):
    acc_tpl = "{:.2%}".format
    loss_tpl = "{:.4f}".format
    epoc_tpl = "{:.0f}".format
    print_order = ['acc','loss','val_acc','val_loss','epoch']

    if short_version:
        print_order = ['val_acc','val_loss']
        stats_df = stats_df[stats_df.index == 'mean']

    if seqs_eval:
        print_order = ['val_acc']

    print(stats_df[print_order].to_string(
        formatters=[acc_tpl,loss_tpl,acc_tpl,loss_tpl,epoc_tpl]))

def print_train_stats(summary_dir, criteria=None, update=False, seqs_eval=False):
    if not seqs_eval: # Central frames only
        summary_filename = '/summary.csv'
    else:
        summary_filename = '/summary-pooled_val_acc.csv'

    if not os.path.exists(summary_dir+summary_filename):
        criteria = 'val_acc'

    if criteria is None:
        summary_df = pd.read_csv(summary_dir+summary_filename, index_col=False)
    else:
        best_epochs = read_runs(summary_dir, criteria=criteria, seqs_eval=seqs_eval)
        if best_epochs == []:
            print("ERROR: Unable to read summary.csv or fit_history.csv")
            return
        summary_df = pd.concat(best_epochs, axis=1, sort=False).T.reset_index(drop=True)

    summary_df.drop('mean', errors='ignore', inplace=True)
    summary_df.drop('std', errors='ignore', inplace=True)

    if update:
        summary_df.to_csv(summary_dir+summary_filename)

    max = summary_df.loc[summary_df['val_acc'].idxmax()].rename('max')
    mean = summary_df.mean().rename('mean')
    std = summary_df.std().rename('std')
    stats = pd.concat([max,mean,std], axis=1).T

    pretty_print_stats(summary_df, seqs_eval=seqs_eval)
    print(stats[['val_acc']].T.to_string(float_format="{:.1%}".format))

def print_protocol_stats(summary_dir, criteria=None):
    pass

def print_train_stats_all(summary_dirs, **kwargs):
    for summary_dir in summary_dirs:
        if summary_dir.endswith('/hp_search/'):
            continue
        print('********** '+summary_dir+' **********')
        print_train_stats(summary_dir, **kwargs)

#%% Main
if __name__ == '__main__':
    args = vars(load_args())

    print('> Starting HyperParameter Search - ', time.asctime( time.localtime(time.time()) ))

    print_args = args.pop('print_args')
    if print_args:
        print("Program arguments and values:")
        for argument, value in args.items():
            print('\t', argument, ":", value)

    print_train_stats_all(**args)

    print('\n> Finished HyperParameter Search -', time.asctime( time.localtime(time.time()) ))


import sys
import struct as st
import math
import multiprocessing as mp
import gzip
import os

def filterstats(SERFACES,SWATHS,TILES):
    filters = []
    for surface in SERFACES:
        for swath in SWATHS:
            for tile in TILES:
                filename= "s_4_"+ surface + swath + tile + ".filter"
                print(filename)
                file = open(filename,"rb")
                file.read(8)
                numberClusters = st.unpack("I",file.read(4))[0]
                bytes = file.read()
                file.close()
                data = st.unpack(str(numberClusters)+"B",bytes)
                print(sum(data))
                filters.append(data)
    return filters

def bclConverter(args):
    def readBCL(foldername, filename, fileExtention):
        file = open(foldername+filename+fileExtention,"rb")
        hbytes = file.read(4) # remove first 4 bytes
        nClusters = st.unpack('I',hbytes)[0]
        dbytes = file.read()
        print(nClusters)
        print(foldername + filename)
        data = st.unpack(str(nClusters)+'B',dbytes)
        file.close()
        return nClusters, data

    def readFasterq(filename,readlen):
        file = gzip.open(filename,"rb")
        hbytes = file.read(4)
        nClusters = st.unpack('I',hbytes)[0]
        dbytes = file.read()
        data = st.unpack(str(nClusters*readlen)+'B',dbytes)
        file.close()
        return nClusters, data

    def filterData(data,filters):
        newClusters = sum(filters)
        filteredData = [point for i, point in enumerate(data) if filters[i]]
        return filteredData, newClusters

    def extractBQ(data):
        bases =  [i%4 for i in data]
        qualities= [i//4 for i in data]
        return qualities, bases

    def remapQualities(qualities,qualityMap):
        remapedQualities = [qualityMap[i] for i in qualities]
        return remapedQualities

    def join(array, bytesToJoin):
        lengthOfNewArray = int(math.ceil(len(array)/float(bytesToJoin)))
        pShift = int(8//bytesToJoin)
        joined = [0] * lengthOfNewArray
        maxMod = bytesToJoin -1
        for i in range(len(array)):
            newindex = int(i//bytesToJoin)
            shift = 2**((maxMod-(i%bytesToJoin))*pShift)
            joined[newindex] = joined[newindex] + array[i]*shift
        return joined

    def saveArray(data,header, foldername, filename,fileExtention):
        hbytes = st.pack('I',header)
        dbytes = st.pack(str(len(data)) +'B',*data)
        outfile=gzip.open(foldername+filename+fileExtention,'w')
        outfile.write(hbytes)
        outfile.write(dbytes)

    def interleave(array1,array2):
        interleved = [j for i in zip(array1,array2) for j in i]
        return interleved

    def basicConverter(foldername,filename,filters):
        OrigonalClusters, data = readBCL(foldername, filename, ".bcl")
        data, OrigonalClusters = filterData(data,filters)
        qualities, bases = extractBQ(data)
        del data
        qualityMap = {0:0, 7:11, 11:11, 22:27, 27:27, 32:27, 37:42, 42:42}
        qualities = remapQualities(qualities, qualityMap)
        data = [((q*4) + bases[i]) for i,q in enumerate(qualities)]
        del qualities, bases
        saveArray(data,OrigonalClusters,foldername,filename,".frrbcl.gz")

    def filterAndConvert(foldername,filename,filters):
        OrigonalClusters, data = readBCL(foldername, filename)
        data,newClusters = filterData(data,filters)
        saveArray(data,newClusters,foldername,filename,".fbcl.gz")

    def JSDbases(filename,CYCLES,readnum):
        read = []
        for cycle in CYCLES:
            foldername = "./C" + cycle + ".1/"
            OrigonalClusters, data =  readBCL(foldername, filename, ".bcl")
            qualities, bases = extractBQ(data)
            del data, qualities
            read.append(bases)
            del bases
        readTf = flatten2d(transpose(read))
        del read
        readTf = join(readTf,4)
        saveArray(readTf,OrigonalClusters,"./",filename+readnum,".JSDbases.gz")
        del readTf

    def JSRRDqualities(filename,CYCLES,readnum):
        read = []
        for cycle in CYCLES:
            foldername = "./C" + cycle + ".1/"
            OrigonalClusters, data =  readBCL(foldername, filename, ".bcl")
            qualities, bases = extractBQ(data)
            del data, bases
            qualityMap = {0:0, 7:1, 11:1, 22:2, 27:2, 32:2, 37:3, 42:3}
            qualities = remapQualities(qualities, qualityMap)
            read.append(qualities)
            del qualities
        readTf = flatten2d(transpose(read))
        del read
        readTf = join(readTf,4)
        saveArray(readTf,OrigonalClusters,"./",filename+readnum,".JSRRDqualities.gz")
        del readTf

    def FJSDbases(filename,CYCLES,readnum,filters):
        read = []
        for cycle in CYCLES:
            foldername = "./C" + cycle + ".1/"
            OrigonalClusters, data =  readBCL(foldername, filename, ".bcl.gz")
            qualities, bases = extractBQ(data)
            bases, OrigonalClusters = filterData(bases,filters)
            del data, qualities
            read.append(bases)
            del bases
        readTf = flatten2d(transpose(read))
        del read
        readTf = join(readTf,4)
        saveArray(readTf,OrigonalClusters,"./",filename+readnum,".FJSDbases.gz")
        del readTf

    def FJSRRDqualities(filename,CYCLES,readnum,filters):
        read = []
        for cycle in CYCLES:
            foldername = "./C" + cycle + ".1/"
            OrigonalClusters, data =  readBCL(foldername, filename, ".bcl.gz")
            data, OrigonalClusters = filterData(data,filters)
            qualities, bases = extractBQ(data)
            del data, bases
            qualityMap = {0:0, 7:1, 11:1, 22:2, 27:2, 32:2, 37:3, 42:3}
            qualities = remapQualities(qualities, qualityMap)
            read.append(qualities)
            del qualities
        readTf = flatten2d(transpose(read))
        del read
        readTf = join(readTf,4)
        saveArray(readTf,OrigonalClusters,"./",filename+readnum,".FJSRRDqualities.gz")
        del readTf

    def demultiplexAndFilter(filename,CYCLES,readnum,filters):
        read = []
        for cycle in CYCLES:
            foldername = "./C" + cycle + ".1/"
            OrigonalClusters, data =  readBCL(foldername, filename)
            read.append(data)
        readTf, newClusters = filterData(transpose(read),filters)
        readTf = flatten2d(readTf)
        saveArray(readTf,newClusters,"./",filename+readnum,".ffasterq.gz")

    def convertFastq(filename,readlen):
        OrigonalClusters, data = readFasterq(filename+".fasterq.gz",readlen)
        qualities, bases = extractBQ(data)
        del data
        del qualities
        #qualityMap = {0:0, 7:1, 11:1, 22:2, 27:2, 32:2, 37:3, 42:3}
        #qualities = remapQualities(qualities, qualityMap)
        #data = interleave(qualities,bases)
        #del qualities
        #del bases
        bases = join(bases,4)
        saveArray(bases, OrigonalClusters, "./", filename, ".dbases.gz")

    def transpose(array):
        transposedRead = list(map(list,zip(*array)))
        return transposedRead

    def flatten2d(array):
        return [i for sublist in array for i in sublist]

    FJSRRDqualities(*args)

if __name__ == "__main__":

    CYCLES = tuple(str(i) for i in range(1,303))
    SERFACES = ("1","2")
    SWATHS = ("1","2")
    TILES = tuple("{:02n}".format(i) for i in range(1,25))
    READS = ("1","2")
    filters= filterstats(SERFACES,SWATHS,TILES)
    #for cycle in CYCLES:
    #pool=mp.Pool()
    sst = 0

    for serface in SERFACES:
        for swath in SWATHS:
            for tile in TILES:
                for read in READS:
                    pool = mp.Pool()
                    #foldername = "./C" + cycle + ".1/"
                    filename ="s_4_" + serface + swath + tile
                    #if filename not in ["s_4_11{:02n}".format(i) for i in range(1,18)]:
                    pool.apply_async(bclConverter,args=([filename,CYCLES[0+(int(read)-1)*151:151+(int(read)-1)*151],read,filters[sst]],))
                    #bclConverter([filename,CYCLES[0+(int(read)-1)*151:151+(int(read)-1)*151],read,filters[sst]])
                    #pool.apply_async(bclConverter,args=([foldername,filename,filters[sst]],))

                    pool.close()
                    pool.join()
                sst += 1