Skip to content

Instantly share code, notes, and snippets.

@Ionizing
Created June 22, 2024 15:28
Show Gist options
  • Save Ionizing/8f4d79145f74cadb353d438d34445215 to your computer and use it in GitHub Desktop.
Save Ionizing/8f4d79145f74cadb353d438d34445215 to your computer and use it in GitHub Desktop.
MoS2 monolayer schematic view of valleys band structure.
#!/usr/bin/env python3
from enum import Enum, unique
import numpy as np
import matplotlib as mpl
import matplotlib.pyplot as plt
from matplotlib.patches import Ellipse
mpl.rcParams["font.sans-serif"] = "monospace"
mpl.rcParams["text.usetex"] = True
mpl.rcParams["text.latex.preamble"] = " ".join([
r"\usepackage{physics}",
])
KWIDTH = 0.7
KX = np.linspace(-KWIDTH, +KWIDTH, 51)
@unique
class Spin(Enum):
Up = 1
Down = -1
@unique
class CircularPolarization(Enum):
Left = 1
Right = -1
def single_band(ax, a=1.0, x0=0.0, y0=0.0, spin=Spin.Up):
y = a * (KX ** 2) + y0
x = KX + x0
color = "r" if spin == Spin.Up else "b"
if spin == Spin.Up:
color = "r"
text = r"${\ket{\uparrow}}$"
else:
color = "b"
text = r"$\ket{\downarrow}$"
ax.plot(x, y, color=color, lw=1.5)
ax.text(x[-1]+0.13, y[-1], text, va="center", ha="center", color=color)
return (x, y)
def arrow_with_circular_polarization(ax, p1=(0.0, 0.0), p2=(0.0, 1.0), polarization=CircularPolarization.Left):
mid = ((p2[0] + p1[0])/2.0, (p2[1] + p1[1])/2.0)
ax.annotate("", p1, p2, zorder=4.0,
arrowprops=dict(
arrowstyle="<->",
shrinkA=0.0,
shrinkB=0.0,
linestyle="--"))
if polarization == CircularPolarization.Left:
color = "tab:orange"
posData = (mid[0] + 0.125, mid[1] + 0.01)
posText = (mid[0] + 0.125, mid[1] + 0.00)
polText = r"$\sigma^+$"
else:
color = "tab:green"
posData = (mid[0] - 0.125, mid[1] + 0.01)
posText = (mid[0] - 0.125, mid[1] + 0.00)
polText = r"$\sigma^-$"
ellipse = Ellipse(xy=mid, width=0.25, height=0.1, edgecolor=color, fc="None", lw=1.0)
ax.add_patch(ellipse)
ax.annotate("", posData, posText, zorder=5.0,
va="center", ha="center",
arrowprops=dict(arrowstyle="->,head_length=0.2",
shrinkA=0.0,
shrinkB=0.0,
color=color,
lw=0.7))
ax.text(mid[0] + 0.25, mid[1]+0.00, polText, color=color, ha="center", va="center")
pass
if '__main__' == __name__:
fig, ax = plt.subplots(figsize=(4, 3))
K0 = 1.0
gap = 0.4
# CBM, K+u & K-d
single_band(ax, a=1.25, x0= K0, y0=gap, spin=Spin.Up)
single_band(ax, a=1.25, x0=-K0, y0=gap, spin=Spin.Down)
# CB, K+d & K-u
single_band(ax, a=1.0, x0= K0, y0=gap+0.015, spin=Spin.Down)
single_band(ax, a=1.0, x0=-K0, y0=gap+0.015, spin=Spin.Up)
# VBM, K+u & K-d
single_band(ax, a=-1.0, x0= K0, y0=0, spin=Spin.Up)
xkp, ykp = single_band(ax, a=-1.0, x0=-K0, spin=Spin.Down, y0=0)
# VB, K+d & K-u
single_band(ax, a=-1.25, x0= K0, y0=-0.05, spin=Spin.Down)
xkm, ykm = single_band(ax, a=-1.25, x0=-K0, y0=-0.05, spin=Spin.Up)
# arrow with circular polarization
arrow_with_circular_polarization(ax, ( K0, 0.0), ( K0, gap), CircularPolarization.Left)
arrow_with_circular_polarization(ax, (-K0, 0.0), (-K0, gap), CircularPolarization.Right)
# labeling K+ and K- valley
ax.text( K0, ykp.min() - 0.1, r"K$^+$", ha="center", va="center", weight="bold")
ax.text(-K0, ykp.min() - 0.1, r"K$^-$", ha="center", va="center", weight="bold")
# Fermi level
ax.axhline(y=0.02, ls="--", lw=0.3, color="k")
ax.text(-K0-KWIDTH, 0.03, r"E\textsubscript{F}", color="k", ha="center", va="bottom")
ax.axis('off')
fig.tight_layout(pad=0.5)
fig.savefig("schematic_band.png", dpi=400)
fig.savefig("schematic_band.pdf", dpi=400)
fig.savefig("schematic_band.svg", dpi=400)
@Ionizing
Copy link
Author

schematic_band

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment