TB2J 0.9.11.2__tar.gz → 0.9.11.3__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/PKG-INFO +1 -1
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/magnon/magnon3.py +58 -21
- tb2j-0.9.11.3/TB2J/magnon/plot_magnon_dos_cli.py +211 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J.egg-info/PKG-INFO +1 -1
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/pyproject.toml +1 -1
- tb2j-0.9.11.2/TB2J/magnon/plot_magnon_dos_cli.py +0 -99
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/LICENSE +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/README.md +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/Jdownfolder.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/Jtensor.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/MAE.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/MAEGreen.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/Oiju.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/Oiju_epc.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/__init__.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/anisotropy.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/basis.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/citation.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/contour.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/density_matrix.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/downfold/Hdownfolder.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/epc.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/exchange.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/exchangeCL2.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/exchange_params.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/exchange_pert.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/exchange_qspace.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/external/__init__.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/external/p_tqdm.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/gpaw_wrapper.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/green.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/greentest.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/__init__.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/abacus/__init__.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/abacus/abacus_api.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/abacus/abacus_wrapper.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/abacus/gen_exchange_abacus.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/abacus/orbital_api.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/abacus/stru_api.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/abacus/test_density_matrix.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/abacus/test_read_HRSR.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/abacus/test_read_stru.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/gpaw_interface.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/lawaf_interface.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/manager.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/siesta_interface.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/interfaces/wannier90_interface.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/io_exchange/__init__.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/io_exchange/io_exchange.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/io_exchange/io_multibinit.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/io_exchange/io_tomsasd.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/io_exchange/io_txt.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/io_exchange/io_uppasd.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/io_exchange/io_vampire.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/io_merge.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/kpoints.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/magnon/__init__.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/magnon/io_exchange2.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/magnon/magnon_band.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/magnon/magnon_dos.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/magnon/magnon_io.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/magnon/magnon_math.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/magnon/plot.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/magnon/structure.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/mathutils/__init__.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/mathutils/auto_kpath.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/mathutils/fermi.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/mathutils/fibonacci_sphere.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/mathutils/kR_convert.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/mathutils/lowdin.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/mathutils/rotate_spin.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/myTB.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/mycfr.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/orbital_magmom.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/orbmap.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/pauli.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/pert.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/plot.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/rotate_atoms.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/rotate_siestaDM.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/TB2J_downfold.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/TB2J_eigen.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/TB2J_magnon.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/TB2J_magnon2.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/TB2J_magnon_dos.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/TB2J_merge.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/TB2J_plot_magnon_bands.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/TB2J_rotate.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/TB2J_rotateDM.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/__init__.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/abacus2J.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/siesta2J.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/scripts/wann2J.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/sisl_wrapper.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/spinham/__init__.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/spinham/base_parser.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/spinham/constants.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/spinham/hamiltonian.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/spinham/hamiltonian_terms.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/spinham/plot.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/spinham/qsolver.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/spinham/spin_api.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/spinham/spin_xml.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/spinham/supercell.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/symmetrize_J.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/tensor_rotate.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/thetaphi.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/utest.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/utils.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/versioninfo.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/wannier/__init__.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/wannier/w90_parser.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J/wannier/w90_tb_parser.py +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J.egg-info/SOURCES.txt +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J.egg-info/dependency_links.txt +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J.egg-info/entry_points.txt +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J.egg-info/requires.txt +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/TB2J.egg-info/top_level.txt +0 -0
- {tb2j-0.9.11.2 → tb2j-0.9.11.3}/setup.cfg +0 -0
@@ -31,6 +31,7 @@ class MagnonParameters:
|
|
31
31
|
Q: Optional[List[float]] = None
|
32
32
|
uz_file: Optional[str] = None
|
33
33
|
n: Optional[List[float]] = None
|
34
|
+
spin_conf_file: Optional[str] = None
|
34
35
|
show: bool = False
|
35
36
|
|
36
37
|
@classmethod
|
@@ -57,6 +58,8 @@ class MagnonParameters:
|
|
57
58
|
# Convert path to absolute path if uz_file is relative to it
|
58
59
|
if self.uz_file and not Path(self.uz_file).is_absolute():
|
59
60
|
self.uz_file = str(Path(self.path) / self.uz_file)
|
61
|
+
if self.spin_conf_file and not Path(self.spin_conf_file).is_absolute():
|
62
|
+
self.spin_conf_file = str(Path(self.path) / self.spin_conf_file)
|
60
63
|
|
61
64
|
|
62
65
|
@dataclass
|
@@ -76,7 +79,7 @@ class Magnon:
|
|
76
79
|
_n: np.ndarray
|
77
80
|
pbc: tuple = (True, True, True)
|
78
81
|
|
79
|
-
def set_reference(self, Q, uz, n):
|
82
|
+
def set_reference(self, Q, uz, n, magmoms=None):
|
80
83
|
"""
|
81
84
|
Set reference propagation vector and quantization axis
|
82
85
|
|
@@ -92,6 +95,8 @@ class Magnon:
|
|
92
95
|
self.set_propagation_vector(Q)
|
93
96
|
self._uz = np.array(uz, dtype=float)
|
94
97
|
self._n = np.array(n, dtype=float)
|
98
|
+
if magmoms is not None:
|
99
|
+
self.magmom = np.array(magmoms, dtype=float)
|
95
100
|
|
96
101
|
def set_propagation_vector(self, Q):
|
97
102
|
"""Set propagation vector"""
|
@@ -653,26 +658,40 @@ def plot_magnon_bands_from_TB2J(
|
|
653
658
|
)
|
654
659
|
|
655
660
|
# Set reference vectors if provided
|
656
|
-
|
657
|
-
|
658
|
-
|
659
|
-
|
660
|
-
|
661
|
-
|
662
|
-
|
663
|
-
|
664
|
-
|
665
|
-
|
666
|
-
|
667
|
-
|
668
|
-
|
669
|
-
|
670
|
-
|
671
|
-
|
672
|
-
|
673
|
-
|
661
|
+
Q = [0, 0, 0] if params.Q is None else params.Q
|
662
|
+
n = [0, 0, 1] if params.n is None else params.n
|
663
|
+
|
664
|
+
# Handle quantization axes
|
665
|
+
if params.uz_file is not None:
|
666
|
+
uz = np.loadtxt(params.uz_file)
|
667
|
+
if uz.shape[1] != 3:
|
668
|
+
raise ValueError(
|
669
|
+
f"Quantization axes file should contain a natom×3 array. Got shape {uz.shape}"
|
670
|
+
)
|
671
|
+
if uz.shape[0] != magnon.nspin:
|
672
|
+
raise ValueError(
|
673
|
+
f"Number of spins in uz file ({uz.shape[0]}) does not match the system ({magnon.nspin})"
|
674
|
+
)
|
675
|
+
else:
|
676
|
+
# Default: [0, 0, 1] for all spins
|
677
|
+
# uz = np.array([[0.0, 0.0, 1.0] for _ in range(magnon.nspin)])
|
678
|
+
uz = np.array([[0, 0, 1]], dtype=float)
|
679
|
+
|
680
|
+
print(params)
|
681
|
+
if params.spin_conf_file is not None:
|
682
|
+
magmoms = np.loadtxt(params.spin_conf_file)
|
683
|
+
if magmoms.shape[1] != 3:
|
684
|
+
raise ValueError(
|
685
|
+
f"Spin configuration file should contain a nspin×3 array. Got shape {magmoms.shape}"
|
686
|
+
)
|
687
|
+
if magmoms.shape[0] != magnon.nspin:
|
688
|
+
raise ValueError(
|
689
|
+
f"Number of spins in spin configuration file ({magmoms.shape[0]}) does not match the system ({magnon.nspin})"
|
690
|
+
)
|
691
|
+
else:
|
692
|
+
magmoms = None
|
674
693
|
|
675
|
-
|
694
|
+
magnon.set_reference(Q, uz, n, magmoms)
|
676
695
|
|
677
696
|
# Get band structure data
|
678
697
|
print(f"\nCalculating bands along path {params.kpath}...")
|
@@ -737,27 +756,32 @@ def main():
|
|
737
756
|
|
738
757
|
# Command line arguments (used if no config file is provided)
|
739
758
|
parser.add_argument(
|
759
|
+
"-p",
|
740
760
|
"--path",
|
741
761
|
default="TB2J_results",
|
742
762
|
help="Path to TB2J results directory (default: TB2J_results)",
|
743
763
|
)
|
744
764
|
parser.add_argument(
|
765
|
+
"-k",
|
745
766
|
"--kpath",
|
746
767
|
default=None,
|
747
768
|
help="k-path specification (default: auto-detected from type of cell)",
|
748
769
|
)
|
749
770
|
parser.add_argument(
|
771
|
+
"-n",
|
750
772
|
"--npoints",
|
751
773
|
type=int,
|
752
774
|
default=300,
|
753
775
|
help="Number of k-points along the path (default: 300)",
|
754
776
|
)
|
755
777
|
parser.add_argument(
|
778
|
+
"-o",
|
756
779
|
"--output",
|
757
780
|
default="magnon_bands.png",
|
758
781
|
help="Output file name (default: magnon_bands.png)",
|
759
782
|
)
|
760
783
|
parser.add_argument(
|
784
|
+
"-j",
|
761
785
|
"--Jiso",
|
762
786
|
action="store_true",
|
763
787
|
default=True,
|
@@ -770,18 +794,21 @@ def main():
|
|
770
794
|
help="Exclude isotropic exchange interactions",
|
771
795
|
)
|
772
796
|
parser.add_argument(
|
797
|
+
"-a",
|
773
798
|
"--Jani",
|
774
799
|
action="store_true",
|
775
800
|
default=False,
|
776
801
|
help="Include anisotropic exchange interactions (default: False)",
|
777
802
|
)
|
778
803
|
parser.add_argument(
|
804
|
+
"-d",
|
779
805
|
"--DMI",
|
780
806
|
action="store_true",
|
781
807
|
default=False,
|
782
808
|
help="Include Dzyaloshinskii-Moriya interactions (default: False)",
|
783
809
|
)
|
784
810
|
parser.add_argument(
|
811
|
+
"-q",
|
785
812
|
"--Q",
|
786
813
|
nargs=3,
|
787
814
|
type=float,
|
@@ -789,11 +816,19 @@ def main():
|
|
789
816
|
help="Propagation vector [Qx, Qy, Qz] (default: [0, 0, 0])",
|
790
817
|
)
|
791
818
|
parser.add_argument(
|
819
|
+
"-u",
|
792
820
|
"--uz-file",
|
793
821
|
type=str,
|
794
|
-
help="Path to file containing quantization axes for each spin (
|
822
|
+
help="Path to file containing quantization axes for each spin (nspin×3 array)",
|
823
|
+
)
|
824
|
+
parser.add_argument(
|
825
|
+
"-c",
|
826
|
+
"--spin-conf-file",
|
827
|
+
type=str,
|
828
|
+
help="Path to file containing magnetic moments for each spin (nspin×3 array)",
|
795
829
|
)
|
796
830
|
parser.add_argument(
|
831
|
+
"-v",
|
797
832
|
"--n",
|
798
833
|
nargs=3,
|
799
834
|
type=float,
|
@@ -802,6 +837,7 @@ def main():
|
|
802
837
|
)
|
803
838
|
|
804
839
|
parser.add_argument(
|
840
|
+
"-s",
|
805
841
|
"--show",
|
806
842
|
action="store_true",
|
807
843
|
default=False,
|
@@ -833,6 +869,7 @@ def main():
|
|
833
869
|
DMI=args.DMI,
|
834
870
|
Q=args.Q if args.Q is not None else None,
|
835
871
|
uz_file=args.uz_file,
|
872
|
+
spin_conf_file=args.spin_conf_file,
|
836
873
|
n=args.n if args.n is not None else None,
|
837
874
|
show=args.show,
|
838
875
|
)
|
@@ -0,0 +1,211 @@
|
|
1
|
+
#!/usr/bin/env python3
|
2
|
+
"""Command-line tool for plotting magnon DOS from TB2J results."""
|
3
|
+
|
4
|
+
import argparse
|
5
|
+
from pathlib import Path
|
6
|
+
|
7
|
+
import numpy as np
|
8
|
+
|
9
|
+
from TB2J.magnon.magnon3 import Magnon
|
10
|
+
from TB2J.magnon.magnon_dos import plot_magnon_dos
|
11
|
+
|
12
|
+
|
13
|
+
def main():
|
14
|
+
parser = argparse.ArgumentParser(
|
15
|
+
description="Calculate and plot magnon DOS from TB2J results"
|
16
|
+
)
|
17
|
+
parser.add_argument(
|
18
|
+
"-p",
|
19
|
+
"--path",
|
20
|
+
default="TB2J_results",
|
21
|
+
help="Path to TB2J results directory (default: TB2J_results)",
|
22
|
+
)
|
23
|
+
parser.add_argument(
|
24
|
+
"--kmesh",
|
25
|
+
type=int,
|
26
|
+
nargs=3,
|
27
|
+
default=[20, 20, 20],
|
28
|
+
metavar=("nx", "ny", "nz"),
|
29
|
+
help="k-point mesh dimensions (default: 20, 20, 20)",
|
30
|
+
)
|
31
|
+
parser.add_argument(
|
32
|
+
"--no-gamma",
|
33
|
+
action="store_false",
|
34
|
+
dest="gamma",
|
35
|
+
help="Exclude Gamma point from k-mesh",
|
36
|
+
)
|
37
|
+
parser.add_argument(
|
38
|
+
"--width",
|
39
|
+
type=float,
|
40
|
+
default=0.001,
|
41
|
+
help="Gaussian smearing width in eV (default: 0.001)",
|
42
|
+
)
|
43
|
+
parser.add_argument(
|
44
|
+
"--window",
|
45
|
+
type=float,
|
46
|
+
nargs=2,
|
47
|
+
metavar=("emin", "emax"),
|
48
|
+
help="Energy window in meV (optional)",
|
49
|
+
)
|
50
|
+
parser.add_argument(
|
51
|
+
"--npts",
|
52
|
+
type=int,
|
53
|
+
default=401,
|
54
|
+
help="Number of energy points (default: 401)",
|
55
|
+
)
|
56
|
+
parser.add_argument(
|
57
|
+
"-o",
|
58
|
+
"--output",
|
59
|
+
default="magnon_dos.png",
|
60
|
+
help="Output filename for plot (default: magnon_dos.png)",
|
61
|
+
)
|
62
|
+
parser.add_argument(
|
63
|
+
"-s",
|
64
|
+
"--show",
|
65
|
+
action="store_true",
|
66
|
+
dest="show",
|
67
|
+
help="Show plot window",
|
68
|
+
)
|
69
|
+
|
70
|
+
# Exchange interaction options (same as in magnon bands)
|
71
|
+
parser.add_argument(
|
72
|
+
"-j",
|
73
|
+
"--Jiso",
|
74
|
+
action="store_true",
|
75
|
+
default=True,
|
76
|
+
help="Include isotropic exchange interactions (default: True)",
|
77
|
+
)
|
78
|
+
parser.add_argument(
|
79
|
+
"--no-Jiso",
|
80
|
+
action="store_false",
|
81
|
+
dest="Jiso",
|
82
|
+
help="Exclude isotropic exchange interactions",
|
83
|
+
)
|
84
|
+
parser.add_argument(
|
85
|
+
"-a",
|
86
|
+
"--Jani",
|
87
|
+
action="store_true",
|
88
|
+
default=False,
|
89
|
+
help="Include anisotropic exchange interactions (default: False)",
|
90
|
+
)
|
91
|
+
parser.add_argument(
|
92
|
+
"-d",
|
93
|
+
"--DMI",
|
94
|
+
action="store_true",
|
95
|
+
default=False,
|
96
|
+
help="Include Dzyaloshinskii-Moriya interactions (default: False)",
|
97
|
+
)
|
98
|
+
|
99
|
+
# Reference vector options (same as in magnon bands)
|
100
|
+
parser.add_argument(
|
101
|
+
"-q",
|
102
|
+
"--Q",
|
103
|
+
nargs=3,
|
104
|
+
type=float,
|
105
|
+
metavar=("Qx", "Qy", "Qz"),
|
106
|
+
help="Propagation vector [Qx, Qy, Qz] (default: [0, 0, 0])",
|
107
|
+
)
|
108
|
+
parser.add_argument(
|
109
|
+
"-u",
|
110
|
+
"--uz-file",
|
111
|
+
type=str,
|
112
|
+
help="Path to file containing quantization axes for each spin (nspin×3 array)",
|
113
|
+
)
|
114
|
+
parser.add_argument(
|
115
|
+
"-c",
|
116
|
+
"--spin-conf-file",
|
117
|
+
type=str,
|
118
|
+
help="Path to file containing magnetic moments for each spin (nspin×3 array)",
|
119
|
+
)
|
120
|
+
parser.add_argument(
|
121
|
+
"-v",
|
122
|
+
"--n",
|
123
|
+
nargs=3,
|
124
|
+
type=float,
|
125
|
+
metavar=("nx", "ny", "nz"),
|
126
|
+
help="Normal vector for rotation [nx, ny, nz] (default: [0, 0, 1])",
|
127
|
+
)
|
128
|
+
|
129
|
+
args = parser.parse_args()
|
130
|
+
|
131
|
+
# Check if TB2J results exist
|
132
|
+
if not Path(args.path).exists():
|
133
|
+
raise FileNotFoundError(f"TB2J results not found at {args.path}")
|
134
|
+
|
135
|
+
# Load magnon calculator with exchange interaction options
|
136
|
+
print(f"Loading exchange parameters from {args.path}...")
|
137
|
+
magnon = Magnon.from_TB2J_results(
|
138
|
+
path=args.path, Jiso=args.Jiso, Jani=args.Jani, DMI=args.DMI
|
139
|
+
)
|
140
|
+
|
141
|
+
# Set reference vectors if provided (same logic as in magnon bands)
|
142
|
+
Q = [0, 0, 0] if args.Q is None else args.Q
|
143
|
+
n = [0, 0, 1] if args.n is None else args.n
|
144
|
+
|
145
|
+
# Handle quantization axes
|
146
|
+
if args.uz_file is not None:
|
147
|
+
# Make path relative to TB2J results if not absolute
|
148
|
+
uz_file = args.uz_file
|
149
|
+
if not Path(uz_file).is_absolute():
|
150
|
+
uz_file = str(Path(args.path) / uz_file)
|
151
|
+
|
152
|
+
uz = np.loadtxt(uz_file)
|
153
|
+
if uz.shape[1] != 3:
|
154
|
+
raise ValueError(
|
155
|
+
f"Quantization axes file should contain a nspin×3 array. Got shape {uz.shape}"
|
156
|
+
)
|
157
|
+
if uz.shape[0] != magnon.nspin:
|
158
|
+
raise ValueError(
|
159
|
+
f"Number of spins in uz file ({uz.shape[0]}) does not match the system ({magnon.nspin})"
|
160
|
+
)
|
161
|
+
else:
|
162
|
+
# Default: [0, 0, 1] for all spins
|
163
|
+
uz = np.array([[0, 0, 1]], dtype=float)
|
164
|
+
|
165
|
+
# Handle spin configuration
|
166
|
+
if args.spin_conf_file is not None:
|
167
|
+
# Make path relative to TB2J results if not absolute
|
168
|
+
spin_conf_file = args.spin_conf_file
|
169
|
+
if not Path(spin_conf_file).is_absolute():
|
170
|
+
spin_conf_file = str(Path(args.path) / spin_conf_file)
|
171
|
+
|
172
|
+
magmoms = np.loadtxt(spin_conf_file)
|
173
|
+
if magmoms.shape[1] != 3:
|
174
|
+
raise ValueError(
|
175
|
+
f"Spin configuration file should contain a nspin×3 array. Got shape {magmoms.shape}"
|
176
|
+
)
|
177
|
+
if magmoms.shape[0] != magnon.nspin:
|
178
|
+
raise ValueError(
|
179
|
+
f"Number of spins in spin configuration file ({magmoms.shape[0]}) does not match the system ({magnon.nspin})"
|
180
|
+
)
|
181
|
+
else:
|
182
|
+
magmoms = None
|
183
|
+
|
184
|
+
# Set reference configuration
|
185
|
+
magnon.set_reference(Q, uz, n, magmoms)
|
186
|
+
|
187
|
+
# Convert window from meV to eV if provided
|
188
|
+
window = None
|
189
|
+
if args.window is not None:
|
190
|
+
window = (args.window[0] / 1000, args.window[1] / 1000)
|
191
|
+
|
192
|
+
# Calculate and plot DOS
|
193
|
+
print("\nCalculating magnon DOS...")
|
194
|
+
_dos = plot_magnon_dos(
|
195
|
+
magnon,
|
196
|
+
kmesh=args.kmesh,
|
197
|
+
gamma=args.gamma,
|
198
|
+
width=args.width,
|
199
|
+
window=window,
|
200
|
+
npts=args.npts,
|
201
|
+
filename=args.output,
|
202
|
+
show=args.show,
|
203
|
+
)
|
204
|
+
|
205
|
+
print(f"\nPlot saved to {args.output}")
|
206
|
+
data_file = Path(args.output).with_suffix(".json")
|
207
|
+
print(f"DOS data saved to {data_file}")
|
208
|
+
|
209
|
+
|
210
|
+
if __name__ == "__main__":
|
211
|
+
main()
|
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
|
|
4
4
|
|
5
5
|
[project]
|
6
6
|
name = "TB2J"
|
7
|
-
version = "0.9.11.
|
7
|
+
version = "0.9.11.3"
|
8
8
|
description = "TB2J: First principle to Heisenberg exchange J using tight-binding Green function method"
|
9
9
|
readme = "README.md"
|
10
10
|
license = { text = "BSD-2-Clause" }
|
@@ -1,99 +0,0 @@
|
|
1
|
-
#!/usr/bin/env python3
|
2
|
-
"""Command-line tool for plotting magnon DOS from TB2J results."""
|
3
|
-
|
4
|
-
import argparse
|
5
|
-
from pathlib import Path
|
6
|
-
|
7
|
-
from TB2J.magnon.magnon3 import Magnon
|
8
|
-
from TB2J.magnon.magnon_dos import plot_magnon_dos
|
9
|
-
|
10
|
-
|
11
|
-
def main():
|
12
|
-
parser = argparse.ArgumentParser(
|
13
|
-
description="Calculate and plot magnon DOS from TB2J results"
|
14
|
-
)
|
15
|
-
parser.add_argument(
|
16
|
-
"--path",
|
17
|
-
default="TB2J_results",
|
18
|
-
help="Path to TB2J results directory (default: TB2J_results)",
|
19
|
-
)
|
20
|
-
parser.add_argument(
|
21
|
-
"--kmesh",
|
22
|
-
type=int,
|
23
|
-
nargs=3,
|
24
|
-
default=[20, 20, 20],
|
25
|
-
metavar=("nx", "ny", "nz"),
|
26
|
-
help="k-point mesh dimensions (default: 20, 20, 20)",
|
27
|
-
)
|
28
|
-
parser.add_argument(
|
29
|
-
"--no-gamma",
|
30
|
-
action="store_false",
|
31
|
-
dest="gamma",
|
32
|
-
help="Exclude Gamma point from k-mesh",
|
33
|
-
)
|
34
|
-
parser.add_argument(
|
35
|
-
"--width",
|
36
|
-
type=float,
|
37
|
-
default=0.001,
|
38
|
-
help="Gaussian smearing width in eV (default: 0.001)",
|
39
|
-
)
|
40
|
-
parser.add_argument(
|
41
|
-
"--window",
|
42
|
-
type=float,
|
43
|
-
nargs=2,
|
44
|
-
metavar=("emin", "emax"),
|
45
|
-
help="Energy window in meV (optional)",
|
46
|
-
)
|
47
|
-
parser.add_argument(
|
48
|
-
"--npts",
|
49
|
-
type=int,
|
50
|
-
default=401,
|
51
|
-
help="Number of energy points (default: 401)",
|
52
|
-
)
|
53
|
-
parser.add_argument(
|
54
|
-
"--output",
|
55
|
-
default="magnon_dos.png",
|
56
|
-
help="Output filename for plot (default: magnon_dos.png)",
|
57
|
-
)
|
58
|
-
parser.add_argument(
|
59
|
-
"-show",
|
60
|
-
action="store_true",
|
61
|
-
dest="show",
|
62
|
-
help="Show plot window",
|
63
|
-
)
|
64
|
-
|
65
|
-
args = parser.parse_args()
|
66
|
-
|
67
|
-
# Check if TB2J results exist
|
68
|
-
if not Path(args.path).exists():
|
69
|
-
raise FileNotFoundError(f"TB2J results not found at {args.path}")
|
70
|
-
|
71
|
-
# Load magnon calculator
|
72
|
-
print(f"Loading exchange parameters from {args.path}...")
|
73
|
-
magnon = Magnon.from_TB2J_results(path=args.path)
|
74
|
-
|
75
|
-
# Convert window from meV to eV if provided
|
76
|
-
window = None
|
77
|
-
if args.window is not None:
|
78
|
-
window = (args.window[0] / 1000, args.window[1] / 1000)
|
79
|
-
|
80
|
-
# Calculate and plot DOS
|
81
|
-
print("\nCalculating magnon DOS...")
|
82
|
-
_dos = plot_magnon_dos(
|
83
|
-
magnon,
|
84
|
-
kmesh=args.kmesh,
|
85
|
-
gamma=args.gamma,
|
86
|
-
width=args.width,
|
87
|
-
window=window,
|
88
|
-
npts=args.npts,
|
89
|
-
filename=args.output,
|
90
|
-
show=args.show,
|
91
|
-
)
|
92
|
-
|
93
|
-
print(f"\nPlot saved to {args.output}")
|
94
|
-
data_file = Path(args.output).with_suffix(".json")
|
95
|
-
print(f"DOS data saved to {data_file}")
|
96
|
-
|
97
|
-
|
98
|
-
if __name__ == "__main__":
|
99
|
-
main()
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|