Skip to content

Commit

Permalink
Adding DownloadYamlHdf5Widget
Browse files Browse the repository at this point in the history
For now, I added it at the end of the main EuphonicBaseResultsWidget.
It will only allow to download phonopy.yaml and fc.hdf5. The plots can be downloaded in the corresponding tabs.

I added a method to the model which produce the downloadable files, and left the actual
_download_data method in the widget. I think this is a proper design as the model manipulates data,
the view can provide them.

Still missing the download of single tabs, for now it does not work
  • Loading branch information
mikibonacci committed Dec 3, 2024
1 parent 29c363f commit a0d32f1
Show file tree
Hide file tree
Showing 2 changed files with 18 additions and 66 deletions.
66 changes: 7 additions & 59 deletions src/aiidalab_qe_vibroscopy/app/widgets/euphonicmodel.py
Original file line number Diff line number Diff line change
@@ -1,11 +1,6 @@
import numpy as np
import traitlets as tl
import copy
import json
import base64
import plotly.io as pio
from monty.json import jsanitize
from IPython.display import display

from aiidalab_qe_vibroscopy.utils.euphonic.data_manipulation.intensity_maps import (
AttrDict,
Expand All @@ -15,6 +10,7 @@
par_dict,
par_dict_powder,
export_euphonic_data,
generate_force_constant_instance,
)

from aiidalab_qe_vibroscopy.utils.euphonic.tab_widgets.euphonic_q_planes_widgets import (
Expand Down Expand Up @@ -247,58 +243,10 @@ def curate_path_and_labels(
def _clone(self):
return copy.deepcopy(self)

def download_data(self, _=None):
"""
Download both the ForceConstants and the spectra json files.
"""
force_constants_dict = self.fc.to_dict()

filename = "single_crystal.json"
my_dict = {}
for branch in range(len(self.spectra)):
my_dict[str(branch)] = self.spectra[branch].to_dict()
my_dict.update(
{
"weighting": self.weighting,
"q_spacing": self.q_spacing,
"energy_broadening": self.energy_broadening,
"ebins": self.energy_bins,
"temperature": self.temperature,
}
)
for k in ["weighting", "q_spacing", "temperature"]:
filename += "_" + k + "_" + str(my_dict[k])

# FC download:
json_str = json.dumps(jsanitize(force_constants_dict))
b64_str = base64.b64encode(json_str.encode()).decode()
self._download(payload=b64_str, filename="force_constants.json")

# Powder data download:
json_str = json.dumps(jsanitize(my_dict))
b64_str = base64.b64encode(json_str.encode()).decode()
self._download(payload=b64_str, filename=filename + ".json")

# Plot download:
## Convert the FigureWidget to an image in base64 format
image_bytes = pio.to_image(
self.map_widget.children[1], format="png", width=800, height=600
)
b64_str = base64.b64encode(image_bytes).decode()
self._download(payload=b64_str, filename=filename + ".png")

@staticmethod
def _download(payload, filename):
from IPython.display import Javascript

javas = Javascript(
"""
var link = document.createElement('a');
link.href = 'data:text/json;charset=utf-8;base64,{payload}'
link.download = "{filename}"
document.body.appendChild(link);
link.click();
document.body.removeChild(link);
""".format(payload=payload, filename=filename)
def produce_phonopy_files(self):
# This is used to produce the phonopy files from
# PhonopyCalculation data. The files are phonopy.yaml and force_constants.hdf5
phonopy_yaml, fc_hdf5 = generate_force_constant_instance(
self.node.phonon_bands.creator, mode="download"
)
display(javas)
return phonopy_yaml, fc_hdf5
18 changes: 11 additions & 7 deletions src/aiidalab_qe_vibroscopy/app/widgets/euphonicwidget.py
Original file line number Diff line number Diff line change
Expand Up @@ -190,11 +190,15 @@ def render(self):
self.upload_widget.children[0].observe(self._on_upload_yaml, "_counter")
self.upload_widget.children[1].observe(self._on_upload_hdf5, "_counter")

self.download_widget = DownloadYamlHdf5Widget(model=self._model)
self.download_widget.layout.display = "none"

self.children = [
self.upload_widget,
self.plot_button,
self.loading_widget,
self.tab_widget,
self.download_widget,
]

def _on_reset_uploads_button_clicked(self, change):
Expand Down Expand Up @@ -259,33 +263,33 @@ def _on_first_plot_button_clicked(self, change=None): # basically the render.

self.loading_widget.layout.display = "none"
self.tab_widget.layout.display = "block"
self.download_widget.layout.display = "block"


class DownloadYamlHdf5Widget(ipw.HBox):
def __init__(self, phonopy_node, **kwargs):
def __init__(self, model):
self._model = model

self.download_button = ipw.Button(
description="Download phonopy data",
icon="pencil",
button_style="primary",
disabled=False,
layout=ipw.Layout(width="auto"),
)
self.download_button.on_click(self.download_data)
self.node = phonopy_node
self.download_button.on_click(self._download_data)

super().__init__(
children=[
self.download_button,
],
)

def download_data(self, _=None):
def _download_data(self, _=None):
"""
Download both the phonopy.yaml and fc.hdf5 files.
"""
phonopy_yaml, fc_hdf5 = generate_force_constant_instance(
self.node, mode="download"
)
phonopy_yaml, fc_hdf5 = self._model.produce_phonopy_files()
self._download(payload=phonopy_yaml, filename="phonopy" + ".yaml")
self._download(payload=fc_hdf5, filename="fc" + ".hdf5")

Expand Down

0 comments on commit a0d32f1

Please sign in to comment.