Mod: refactoring gui

This commit is contained in:
L-Nafaryus 2022-02-12 13:58:24 +05:00
parent 13e02b57a4
commit fea53d0db7
No known key found for this signature in database
GPG Key ID: C76D8DCD2727DBB7
9 changed files with 186 additions and 126 deletions

View File

@ -34,7 +34,7 @@ def init(path, verbose):
core_utils.setupLogger(utils.verbose_level(verbose)) core_utils.setupLogger(utils.verbose_level(verbose))
logger = logging.getLogger(__name__) logger = logging.getLogger(__name__)
config = config.default_config() config = core_config.default_config()
filepath = os.path.abspath(os.path.join(path, "anisotropy.toml")) filepath = os.path.abspath(os.path.join(path, "anisotropy.toml"))
logger.info(f"Saving file at { filepath }") logger.info(f"Saving file at { filepath }")
@ -165,7 +165,7 @@ def compute(path, configFile, nprocs, stage, overwrite, params, verbose, executi
def gui(path, verbose): def gui(path, verbose):
import anisotropy import anisotropy
from anisotropy.core import utils as core_utils from anisotropy.core import utils as core_utils
from anisotropy.gui import app from anisotropy import gui
anisotropy.loadEnv() anisotropy.loadEnv()
@ -178,4 +178,4 @@ def gui(path, verbose):
core_utils.setupLogger(utils.verbose_level(verbose)) core_utils.setupLogger(utils.verbose_level(verbose))
# logger = logging.getLogger(__name__) # logger = logging.getLogger(__name__)
app.run_server(debug = True) gui.run(debug = True)

View File

@ -1,7 +1,15 @@
# -*- coding: utf-8 -*- # -*- coding: utf-8 -*-
from .layouts.main import app from . import layouts
from .layouts import app
app.layout = layouts.base
def run(*args, **kwargs):
app.run_server(*args, **kwargs)
if __name__ == "__main__": if __name__ == "__main__":
app.run_server(debug = True) run(debug = True)

View File

@ -4,7 +4,5 @@ import dash
import dash_bootstrap_components as dbc import dash_bootstrap_components as dbc
app = dash.Dash(__name__, external_stylesheets = [ dbc.themes.LUX ]) app = dash.Dash(__name__, external_stylesheets = [ dbc.themes.LUX ])
app.title = "anisotropy" app.title = "Anisotropy"
app.config.update( app.config["update_title"] = None
update_title = None
)

View File

@ -1 +1,29 @@
# -*- coding: utf-8 -*- # -*- coding: utf-8 -*-
from . import (
runner,
settings,
database,
visualization,
about,
base
)
from .base import app
runner = runner.layout
settings = settings.layout
database = database.layout
visualization = visualization.layout
about = about.layout
base = base.layout
__all__ = [
"runner",
"settings",
"database",
"visualization",
"about",
"base",
"app"
]

View File

@ -2,7 +2,7 @@
from dash import html from dash import html
from dash import dcc from dash import dcc
from dash.dependencies import Input, Output, State from dash.dependencies import Input, Output
import dash_bootstrap_components as dbc import dash_bootstrap_components as dbc
from . import ( from . import (
@ -13,31 +13,32 @@ from . import (
about about
) )
from ..app import app from ..app import app
from ..styles import * from .. import styles
import anisotropy import anisotropy
### ###
# Layout # Layout
## ##
app.layout = html.Div([ layout = html.Div([
# Location # Location
dcc.Location(id = "url", refresh = False), dcc.Location(id = "url", refresh = False),
# Sidebar # Sidebar
html.Div([ html.Div([
# Sidebar # Sidebar
html.H2([html.Img(src = "/assets/simple.png", height = "150px")], style = logo), html.H2([html.Img(src = "/assets/simple.png", height = "150px")], style = styles.logo),
html.Hr(style = { "color": "#ffffff" }), html.Hr(style = { "color": "#ffffff" }),
dbc.Nav([ dbc.Nav([
dbc.NavLink("Runner", href = "/", active = "exact", style = white), dbc.NavLink("Runner", href = "/", active = "exact", style = styles.white),
dbc.NavLink("Settings", href = "/settings", active = "exact", style = white), dbc.NavLink("Settings", href = "/settings", active = "exact", style = styles.white),
dbc.NavLink("Database", href = "/database", active = "exact", style = white), dbc.NavLink("Database", href = "/database", active = "exact", style = styles.white),
dbc.NavLink("Visualization", href = "/visualization", active = "exact", style = white), dbc.NavLink("Visualization", href = "/visualization", active = "exact", style = styles.white),
dbc.NavLink("About", href = "/about", active = "exact", style = white), dbc.NavLink("About", href = "/about", active = "exact", style = styles.white),
], vertical = True, pills = True), ], vertical = True, pills = True),
# Misc # Misc
html.Hr(style = white), html.Hr(style = styles.white),
dbc.Container([ dbc.Container([
dbc.Row([ dbc.Row([
dbc.Col("v1.2.0"), dbc.Col("v1.2.0"),
@ -48,12 +49,12 @@ app.layout = html.Div([
) )
) )
]) ])
], style = misc) ], style = styles.misc)
], style = sidebar), ], style = styles.sidebar),
# Content # Content
html.Div(id = "page-content", style = page), html.Div(id = "page-content", style = styles.page),
], style = content) ], style = styles.content)
### ###
@ -78,4 +79,3 @@ def displayPage(pathname):
else: else:
return runner.layout return runner.layout

View File

@ -6,10 +6,11 @@ from dash import dcc
import dash_bootstrap_components as dbc import dash_bootstrap_components as dbc
from dash.dependencies import Input, Output, State from dash.dependencies import Input, Output, State
import os import pathlib
from os import environ
from ..app import app from ..app import app
from ..styles import * from .. import styles
### ###
@ -22,9 +23,9 @@ layout = html.Div([
duration = 10000, duration = 10000,
dismissable = True, dismissable = True,
is_open = False, is_open = False,
style = message style = styles.message
), ),
#dcc.Interval(id = "interval", interval = 1000, n_intervals = 0), # dcc.Interval(id = "interval", interval = 1000, n_intervals = 0),
# Query # Query
html.H2("Database"), html.H2("Database"),
@ -32,20 +33,26 @@ layout = html.Div([
html.P("Query"), html.P("Query"),
dcc.Textarea(id = "db_input", style = { "min-width": "100%"}), dcc.Textarea(id = "db_input", style = { "min-width": "100%"}),
html.Br(), html.Br(),
dbc.Button("Query", id = "query", style = minWidth), dbc.Button("Query", id = "query", style = styles.minWidth),
# Output # Output
html.Hr(), html.Hr(),
html.P("Output"), html.P("Output"),
DataTable(id = "db_output", columns = [], data = [], style_table = { "overflow": "scroll"}, style_cell={ DataTable(
'textAlign': 'left', id = "db_output",
'width': '150px', columns = [],
'minWidth': '180px', data = [],
'maxWidth': '180px', style_table = { "overflow": "scroll"},
'whiteSpace': 'no-wrap', style_cell = {
'overflow': 'hidden', 'textAlign': 'left',
'textOverflow': 'ellipsis', 'width': '150px',
}), 'minWidth': '180px',
'maxWidth': '180px',
'whiteSpace': 'no-wrap',
'overflow': 'hidden',
'textOverflow': 'ellipsis',
}
),
]) ])
@ -63,17 +70,17 @@ layout = html.Div([
prevent_initial_call = True prevent_initial_call = True
) )
def db_query(clicks, db_input): def db_query(clicks, db_input):
from anisotropy.database import Database from anisotropy import database
from peewee import OperationalError import peewee as pw
dbpath = os.path.join(os.environ["ANISOTROPY_CWD"], os.environ["ANISOTROPY_DB_FILE"]) path = pathlib.Path(environ["AP_CWD"], environ["AP_DB_FILE"])
db = Database(path = dbpath) db = database.Database(path)
try: try:
db.connect() db.connect()
cursor = db.execute_sql(db_input) cursor = db.execute_sql(db_input)
except OperationalError as e: except pw.OperationalError as e:
db.close() db.close()
return None, None, str(e), True, "danger" return None, None, str(e), True, "danger"
@ -91,4 +98,4 @@ def db_query(clicks, db_input):
db.close() db.close()
return columns, data, "", False, "success" return columns, data, "", False, "success"

View File

@ -6,11 +6,13 @@ from dash import dcc
import dash_bootstrap_components as dbc import dash_bootstrap_components as dbc
from dash.dependencies import Input, Output, State from dash.dependencies import Input, Output, State
import pathlib
import os import os
from os import environ
from ..app import app from ..app import app
from ..styles import * from .. import styles
from ..utils import getSize from .. import utils
### ###
@ -23,7 +25,7 @@ layout = html.Div([
duration = 10000, duration = 10000,
dismissable = True, dismissable = True,
is_open = False, is_open = False,
style = message style = styles.message
), ),
dcc.Interval(id = "interval", interval = 1000, n_intervals = 0), dcc.Interval(id = "interval", interval = 1000, n_intervals = 0),
@ -31,22 +33,22 @@ layout = html.Div([
html.H2("Runner"), html.H2("Runner"),
html.Hr(), html.Hr(),
html.P("Execution (leave zero for the latest)"), html.P("Execution (leave zero for the latest)"),
dcc.Input(id = "execution", type = "number", value = 0, min = 0, style = minWidth), dcc.Input(id = "execution", type = "number", value = 0, min = 0, style = styles.minWidth),
html.Br(), html.Br(),
dbc.Button("Start", id = "start", color = "success", style = minWidth), dbc.Button("Start", id = "start", color = "success", style = styles.minWidth),
dbc.Button("Stop", id = "stop", color = "danger", disabled = True, style = minWidth), dbc.Button("Stop", id = "stop", color = "danger", disabled = True, style = styles.minWidth),
# Monitor # Monitor
html.H2("Monitor"), html.H2("Monitor"),
html.Hr(), html.Hr(),
html.P(id = "runner-status"), html.P(id = "runner-status"),
DataTable(id = "monitor", columns = [], data = [], style_table = table), DataTable(id = "monitor", columns = [], data = [], style_table = styles.table),
# Log # Log
html.H2("Log"), html.H2("Log"),
html.Hr(), html.Hr(),
dbc.Button("Delete", id = "delete", style = minWidth), dbc.Button("Delete", id = "delete", style = styles.minWidth),
dcc.Textarea(id = "logger", disabled = True, style = bigText) dcc.Textarea(id = "logger", disabled = True, style = styles.bigText)
]) ])
@ -67,10 +69,10 @@ def runnerStart(clicks, execution):
"anisotropy", "anisotropy",
"compute", "compute",
"-v", "-v",
"--path", os.environ["ANISOTROPY_CWD"], "--path", environ["AP_CWD"],
"--conf", os.environ["ANISOTROPY_CONF_FILE"], "--conf", environ["AP_CONF_FILE"],
"--pid", "anisotropy.pid", "--pid", "anisotropy.pid",
"--logfile", os.environ["ANISOTROPY_LOG_FILE"], "--logfile", environ["AP_LOG_FILE"],
] ]
if execution > 0: if execution > 0:
@ -83,6 +85,7 @@ def runnerStart(clicks, execution):
return True return True
@app.callback( @app.callback(
Output("stop", "active"), Output("stop", "active"),
[ Input("stop", "n_clicks") ], [ Input("stop", "n_clicks") ],
@ -92,7 +95,7 @@ def runnerStop(clicks):
import psutil import psutil
import signal import signal
pidpath = os.path.join(os.environ["ANISOTROPY_CWD"], "anisotropy.pid") pidpath = pathlib.Path(environ["AP_CWD"], "anisotropy.pid")
try: try:
pid = int(open(pidpath, "r").read()) pid = int(open(pidpath, "r").read())
@ -107,7 +110,6 @@ def runnerStop(clicks):
return True return True
@app.callback( @app.callback(
Output("monitor", "columns"), Output("monitor", "columns"),
Output("monitor", "data"), Output("monitor", "data"),
@ -120,14 +122,14 @@ def runnerStop(clicks):
def monitorUpdate(intervals): def monitorUpdate(intervals):
import psutil import psutil
pidpath = os.path.join(os.environ["ANISOTROPY_CWD"], "anisotropy.pid") pidpath = pathlib.Path(environ["AP_CWD"], "anisotropy.pid")
processes = [] processes = []
try: try:
pid = int(open(pidpath, "r").read()) pid = int(open(pidpath, "r").read())
master = psutil.Process(pid) master = psutil.Process(pid)
except (FileNotFoundError, psutil.NoSuchProcess) as e: except (FileNotFoundError, psutil.NoSuchProcess):
return [], [], "Status: not running", False, True, False return [], [], "Status: not running", False, True, False
else: else:
@ -137,7 +139,7 @@ def monitorUpdate(intervals):
"name": process.name(), "name": process.name(),
"pid": process.pid, "pid": process.pid,
"status": process.status(), "status": process.status(),
"memory": getSize(process.memory_full_info().uss), "memory": utils.getSize(process.memory_full_info().uss),
"threads": process.num_threads(), "threads": process.num_threads(),
"created": "{}:{}:{}".format(created.tm_hour, created.tm_min, created.tm_sec) "created": "{}:{}:{}".format(created.tm_hour, created.tm_min, created.tm_sec)
}) })
@ -146,12 +148,13 @@ def monitorUpdate(intervals):
return columns, processes, "Status: running", True, False, True return columns, processes, "Status: running", True, False, True
@app.callback( @app.callback(
Output("logger", "value"), Output("logger", "value"),
[ Input("interval", "n_intervals") ] [ Input("interval", "n_intervals") ]
) )
def logUpdate(intervals): def logUpdate(intervals):
logpath = os.path.join(os.environ["ANISOTROPY_CWD"], "anisotropy.log") logpath = pathlib.Path(environ["AP_CWD"], "anisotropy.log")
if os.path.exists(logpath): if os.path.exists(logpath):
with open(logpath, "r") as io: with open(logpath, "r") as io:
@ -169,9 +172,9 @@ def logUpdate(intervals):
prevent_initial_call = True prevent_initial_call = True
) )
def logDelete(clicks): def logDelete(clicks):
logpath = os.path.join(os.environ["ANISOTROPY_CWD"], "anisotropy.log") logpath = pathlib.Path(environ["AP_CWD"], "anisotropy.log")
if os.path.exists(logpath): if os.path.exists(logpath):
os.remove(logpath) os.remove(logpath)
return True return True

View File

@ -5,9 +5,11 @@ from dash import dcc
import dash_bootstrap_components as dbc import dash_bootstrap_components as dbc
from dash.dependencies import Input, Output, State from dash.dependencies import Input, Output, State
import os import pathlib
from os import environ
from ..app import app from ..app import app
from ..styles import * from .. import styles
### ###
@ -20,14 +22,14 @@ layout = html.Div([
duration = 10000, duration = 10000,
dismissable = True, dismissable = True,
is_open = False, is_open = False,
style = message style = styles.message
), ),
dbc.Alert( dbc.Alert(
id = "general-status", id = "general-status",
duration = 10000, duration = 10000,
dismissable = True, dismissable = True,
is_open = False, is_open = False,
style = message style = styles.message
), ),
# General # General
html.H2("General"), html.H2("General"),
@ -35,25 +37,25 @@ layout = html.Div([
html.P("Path"), html.P("Path"),
dcc.Input(id = "cwd", style = { "min-width": "500px" }), dcc.Input(id = "cwd", style = { "min-width": "500px" }),
html.Br(), html.Br(),
dbc.Button("Save general", id = "general-save", style = minWidth), dbc.Button("Save general", id = "general-save", style = styles.minWidth),
# Options # Options
html.H2("Options"), html.H2("Options"),
html.Hr(), html.Hr(),
html.P("Nprocs"), html.P("Nprocs"),
dcc.Input(id = "nprocs", type = "number", style = minWidth), dcc.Input(id = "nprocs", type = "number", style = styles.minWidth),
html.P("Stage"), html.P("Stage"),
dcc.Dropdown( dcc.Dropdown(
id = "stage", id = "stage",
options = [ { "label": k, "value": k } for k in ["all", "shape", "mesh", "flow", "postProcess"] ], options = [ { "label": k, "value": k } for k in ["all", "shape", "mesh", "flow", "postProcess"] ],
style = minWidth style = styles.minWidth
), ),
dbc.Button("Save", id = "submit", style = minWidth), dbc.Button("Save", id = "submit", style = styles.minWidth),
# Cases # Cases
html.H2("Cases"), html.H2("Cases"),
html.Hr(), html.Hr(),
dcc.Textarea(id = "cases", style = bigText), dcc.Textarea(id = "cases", style = styles.bigText),
]) ])
@ -71,13 +73,12 @@ layout = html.Div([
prevent_initial_call = True prevent_initial_call = True
) )
def generalSave(clicks, cwd): def generalSave(clicks, cwd):
if not os.path.abspath(cwd): path = pathlib.Path(cwd)
if not path.is_absolute():
return "Cwd path must be absolute", True, "danger" return "Cwd path must be absolute", True, "danger"
if cwd[-1] == "/": environ["AP_CWD"] = str(path)
cwd = cwd[ :-1]
os.environ["ANISOTROPY_CWD"] = cwd
return "General settings saved", True, "success" return "General settings saved", True, "success"
@ -93,13 +94,13 @@ def settingsLoad(pathname):
from anisotropy.core import config as core_config from anisotropy.core import config as core_config
import toml import toml
filepath = os.path.join(os.environ["ANISOTROPY_CWD"], os.environ["ANISOTROPY_CONF_FILE"]) path = pathlib.Path(environ["AP_CWD"], environ["AP_CONF_FILE"])
config = core_config.default_config() config = core_config.default_config()
if os.path.exists(filepath): if path.exists():
config.load(filepath) config.load(path)
return os.environ["ANISOTROPY_CWD"], config["nprocs"], config["stage"], toml.dumps(config.content) return environ["AP_CWD"], config["nprocs"], config["stage"], toml.dumps(config.content)
@app.callback( @app.callback(
@ -118,11 +119,11 @@ def settingsSave(nclick, nprocs, stage, cases):
from anisotropy.core import config as core_config from anisotropy.core import config as core_config
import toml import toml
filepath = os.path.join(os.environ["ANISOTROPY_CWD"], os.environ["ANISOTROPY_CONF_FILE"]) path = pathlib.Path(environ["AP_CWD"], environ["AP_CONF_FILE"])
config = core_config.default_config() config = core_config.default_config()
if os.path.exists(filepath): if path.exists():
config.load(filepath) config.load(path)
config.update( config.update(
nprocs = nprocs, nprocs = nprocs,
@ -131,10 +132,10 @@ def settingsSave(nclick, nprocs, stage, cases):
try: try:
config.content = toml.loads(cases) config.content = toml.loads(cases)
config.dump(filepath) config.dump(path)
except Exception as e: except Exception as e:
return str(e), True, "danger" return str(e), True, "danger"
else: else:
return f"Saved to { filepath }", True, "success" return f"Saved to { path }", True, "success"

View File

@ -1,6 +1,5 @@
# -*- coding: utf-8 -*- # -*- coding: utf-8 -*-
from dash.dash_table import DataTable
from dash import html from dash import html
from dash import dcc from dash import dcc
import dash_bootstrap_components as dbc import dash_bootstrap_components as dbc
@ -8,7 +7,9 @@ from dash.dependencies import Input, Output, State
import dash_vtk import dash_vtk
import dash_vtk.utils import dash_vtk.utils
import vtk import vtk
import os
import pathlib
from os import environ
from ..app import app from ..app import app
from .. import styles from .. import styles
@ -149,7 +150,10 @@ plotcontrols = html.Div([
html.P("Structure"), html.P("Structure"),
dcc.Dropdown( dcc.Dropdown(
id = "plot-structure", id = "plot-structure",
options = [ { "label": v, "value": v } for v in [ "simple", "bodyCentered", "faceCentered" ] ], options = [
{ "label": v, "value": v }
for v in [ "simple", "bodyCentered", "faceCentered" ]
],
value = "simple" value = "simple"
), ),
html.Br(), html.Br(),
@ -157,7 +161,10 @@ plotcontrols = html.Div([
html.P("Direction"), html.P("Direction"),
dcc.Dropdown( dcc.Dropdown(
id = "plot-direction", id = "plot-direction",
options = [ { "label": str(v), "value": str(v)} for v in [ [1., 0., 0.], [0., 0., 1.], [1., 1., 1.], "all" ] ], options = [
{ "label": str(v), "value": str(v)}
for v in [ [1., 0., 0.], [0., 0., 1.], [1., 1., 1.], "all" ]
],
value = str([1., 0., 0.]), value = str([1., 0., 0.]),
), ),
html.Br(), html.Br(),
@ -185,10 +192,11 @@ layout = html.Div([
width = 8, width = 8,
children = [ children = [
html.Div(id = "plot-output", style = { "width": "100%", "min-width": "800px" }) html.Div(id = "plot-output", style = { "width": "100%", "min-width": "800px" })
] ],
, style = { "min-width": "800px" }), style = { "min-width": "800px" }
),
], style = { "height": "100%"}), ], style = { "height": "100%"}),
]), ]),
html.Br(), html.Br(),
html.H2("Mesh"), html.H2("Mesh"),
@ -201,11 +209,14 @@ layout = html.Div([
dbc.Col( dbc.Col(
width = 8, width = 8,
children = [ children = [
html.Div(id = "vtk-output", style = { "height": "800px", "width": "100%", "min-width": "800px" }) html.Div(
] id = "vtk-output",
, style = { "min-width": "800px" }), style = { "height": "800px", "width": "100%", "min-width": "800px" }
)
],
style = { "min-width": "800px" }),
], style = { "height": "100%"}), ], style = { "height": "100%"}),
]) ])
]) ])
@ -220,19 +231,18 @@ layout = html.Div([
] ]
) )
def plotDraw(clicks, execution, structure, direction, data): def plotDraw(clicks, execution, structure, direction, data):
from os import path
from peewee import JOIN from peewee import JOIN
from anisotropy.database import Database, models from anisotropy.database import Database, tables
import json import json
from pandas import DataFrame from pandas import DataFrame
import plotly.express as px import plotly.express as px
dbpath = path.join(os.environ["ANISOTROPY_CWD"], os.environ["ANISOTROPY_DB_FILE"]) path = pathlib.Path(environ["AP_CWD"], environ["AP_DB_FILE"])
if not path.isfile(dbpath): if not path.is_file():
return [ "Database not found" ] return [ "Database not found" ]
db = Database(path = dbpath) db = Database(path)
if not db.getExecution(execution): if not db.getExecution(execution):
return [ "Execution not found" ] return [ "Execution not found" ]
@ -241,33 +251,35 @@ def plotDraw(clicks, execution, structure, direction, data):
try: try:
column = getattr(model, data) column = getattr(model, data)
except AttributeError as e: except AttributeError:
pass pass
else: else:
break break
if direction == "all": if direction == "all":
select = (models.Shape.alpha, column, models.Shape.direction) select = (tables.Shape.alpha, column, tables.Shape.direction)
else: else:
select = (models.Shape.alpha, column) select = (tables.Shape.alpha, column)
query = ( query = (
models.Shape tables.Shape
.select(*select) .select(*select)
.join(models.Execution, JOIN.LEFT_OUTER) .join(tables.Execution, JOIN.LEFT_OUTER)
.switch(models.Shape) .switch(tables.Shape)
.join(models.Mesh, JOIN.LEFT_OUTER) .join(tables.Mesh, JOIN.LEFT_OUTER)
.switch(models.Shape) .switch(tables.Shape)
# .join(tables.FlowOnephase, JOIN.LEFT_OUTER)
# .switch(tables.Shape)
.where( .where(
models.Shape.exec_id == execution, tables.Shape.exec_id == execution,
models.Shape.label == structure, tables.Shape.label == structure,
) )
) )
if not direction == "all": if not direction == "all":
query = query.where(models.Shape.direction == json.loads(direction)) query = query.where(tables.Shape.direction == json.loads(direction))
with db: with db:
if query.exists(): if query.exists():
@ -305,8 +317,8 @@ def plotDraw(clicks, execution, structure, direction, data):
) )
fig.layout.template = "custom_dark" fig.layout.template = "custom_dark"
fig.update_xaxes(showline=True, linewidth=1, linecolor='#4f687d', mirror=True) fig.update_xaxes(showline = True, linewidth = 1, linecolor = '#4f687d', mirror = True)
fig.update_yaxes(showline=True, linewidth=1, linecolor='#4f687d', mirror=True) fig.update_yaxes(showline = True, linewidth = 1, linecolor = '#4f687d', mirror = True)
plot = dcc.Graph( plot = dcc.Graph(
figure = fig figure = fig
@ -315,7 +327,6 @@ def plotDraw(clicks, execution, structure, direction, data):
return [ plot ] return [ plot ]
@app.callback( @app.callback(
[ Output("alpha", "min"), Output("alpha", "max") ], [ Output("alpha", "min"), Output("alpha", "max") ],
[ Input("structure", "value") ] [ Input("structure", "value") ]
@ -330,6 +341,7 @@ def alphaLimits(label):
elif label == "faceCentered": elif label == "faceCentered":
return 0.01, 0.13 return 0.01, 0.13
@app.callback( @app.callback(
[ Output("vtk-output", "children") ], [ Output("vtk-output", "children") ],
[ Input("draw", "n_clicks") ], [ Input("draw", "n_clicks") ],
@ -351,19 +363,22 @@ def alphaLimits(label):
prevent_initial_call = True prevent_initial_call = True
) )
def meshDraw(clicks, execution, structure, direction, alpha, clip, crinkle, wireframe, normal_x, normal_y, normal_z, origin_x, origin_y, origin_z): def meshDraw(clicks, execution, structure, direction, alpha, clip, crinkle, wireframe, normal_x, normal_y, normal_z, origin_x, origin_y, origin_z):
from os import path
import meshio import meshio
path = pathlib.Path(environ["AP_CWD"], environ["AP_BUILD_DIR"])
path /= "execution-{}".format(execution)
path /= "{}-{}-{}".format(
structure,
direction.replace(" ", ""),
alpha
)
basemeshpath = path / "mesh.msh"
meshpath = path / "mesh.vtu"
execution = "execution-{}".format(execution) if not basemeshpath.exists():
case = "{}-{}-{}".format(structure, direction.replace(" ", ""), alpha)
casepath = path.join(os.environ["ANISOTROPY_CWD"], os.environ["ANISOTROPY_BUILD_DIR"], execution, case)
basemeshpath = path.join(casepath, "mesh.msh")
meshpath = path.join(casepath, "mesh.vtu")
if not path.exists(basemeshpath):
return [ "Mesh not found" ] return [ "Mesh not found" ]
if not path.exists(meshpath) or not path.isfile(meshpath): if not meshpath.exists() or not meshpath.is_file():
meshold = meshio.read(basemeshpath) meshold = meshio.read(basemeshpath)
meshold.write(meshpath) meshold.write(meshpath)