{ "cells": [ { "cell_type": "markdown", "id": "00940c64-4748-4b08-9a35-ea98ce311e71", "metadata": {}, "source": [ "## LG M50 Single Pulse Parameter Identification\n", "\n", "This example presents an experimental parameter identification method for a two-RC circuit model. The data for this notebook is located within the same directory and was obtained from [[1]](https://github.com/WDWidanage/Simscape-Battery-Library/tree/main/Examples/parameterEstimation_TECMD/Data).\n", "\n", "\n", "### Setting up the Environment\n", "\n", "Before we begin, we need to ensure that we have all the necessary tools. We will install PyBOP for the fitting and Pandas for the data ingestion and manipulation:" ] }, { "cell_type": "code", "execution_count": 1, "id": "dd0e1a20-1ba3-4ff5-8f6a-f9c6f25c2a4a", "metadata": { "execution": { "iopub.execute_input": "2024-04-14T18:57:35.622247Z", "iopub.status.busy": "2024-04-14T18:57:35.621773Z", "iopub.status.idle": "2024-04-14T18:57:40.672493Z", "shell.execute_reply": "2024-04-14T18:57:40.671959Z" } }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Requirement already satisfied: pip in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (24.0)\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ "Requirement already satisfied: ipywidgets in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (8.1.2)\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ "Requirement already satisfied: comm>=0.1.3 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from ipywidgets) (0.2.2)\r\n", "Requirement already satisfied: ipython>=6.1.0 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from ipywidgets) (8.23.0)\r\n", "Requirement already satisfied: traitlets>=4.3.1 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from ipywidgets) (5.14.2)\r\n", "Requirement already satisfied: widgetsnbextension~=4.0.10 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from ipywidgets) (4.0.10)\r\n", "Requirement already satisfied: jupyterlab-widgets~=3.0.10 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from ipywidgets) (3.0.10)\r\n", "Requirement already satisfied: decorator in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from ipython>=6.1.0->ipywidgets) (5.1.1)\r\n", "Requirement already satisfied: jedi>=0.16 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from ipython>=6.1.0->ipywidgets) (0.19.1)\r\n", "Requirement already satisfied: matplotlib-inline in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from ipython>=6.1.0->ipywidgets) (0.1.6)\r\n", "Requirement already satisfied: prompt-toolkit<3.1.0,>=3.0.41 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from ipython>=6.1.0->ipywidgets) (3.0.43)\r\n", "Requirement already satisfied: pygments>=2.4.0 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from ipython>=6.1.0->ipywidgets) (2.17.2)\r\n", "Requirement already satisfied: stack-data in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from ipython>=6.1.0->ipywidgets) (0.6.3)\r\n", "Requirement already satisfied: pexpect>4.3 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from ipython>=6.1.0->ipywidgets) (4.9.0)\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ "Requirement already satisfied: parso<0.9.0,>=0.8.3 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from jedi>=0.16->ipython>=6.1.0->ipywidgets) (0.8.4)\r\n", "Requirement already satisfied: ptyprocess>=0.5 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from pexpect>4.3->ipython>=6.1.0->ipywidgets) (0.7.0)\r\n", "Requirement already satisfied: wcwidth in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from prompt-toolkit<3.1.0,>=3.0.41->ipython>=6.1.0->ipywidgets) (0.2.13)\r\n", "Requirement already satisfied: executing>=1.2.0 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from stack-data->ipython>=6.1.0->ipywidgets) (2.0.1)\r\n", "Requirement already satisfied: asttokens>=2.1.0 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from stack-data->ipython>=6.1.0->ipywidgets) (2.4.1)\r\n", "Requirement already satisfied: pure-eval in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from stack-data->ipython>=6.1.0->ipywidgets) (0.2.2)\r\n", "Requirement already satisfied: six>=1.12.0 in /Users/engs2510/.pyenv/versions/pybop-3.12/lib/python3.12/site-packages (from asttokens>=2.1.0->stack-data->ipython>=6.1.0->ipywidgets) (1.16.0)\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ "Note: you may need to restart the kernel to use updated packages.\n", "zsh:1: no matches found: pybop[plot]\r\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ "Note: you may need to restart the kernel to use updated packages.\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ "Note: you may need to restart the kernel to use updated packages.\n" ] } ], "source": [ "%pip install --upgrade pip ipywidgets\n", "%pip install pybop[plot] -q\n", "%pip install pandas -q" ] }, { "cell_type": "markdown", "id": "90efc3d3-bf00-423d-ba81-246e4763b499", "metadata": {}, "source": [ "### Importing Libraries\n", "\n", "With the environment set up, we can now import PyBOP alongside other libraries we will need:" ] }, { "cell_type": "code", "execution_count": 2, "id": "d6afb8f9-3872-4a7e-a76d-0b50855fe089", "metadata": { "execution": { "iopub.execute_input": "2024-04-14T18:57:40.675505Z", "iopub.status.busy": "2024-04-14T18:57:40.675195Z", "iopub.status.idle": "2024-04-14T18:57:46.231644Z", "shell.execute_reply": "2024-04-14T18:57:46.230956Z" } }, "outputs": [], "source": [ "import pandas as pd\n", "import plotly.graph_objects as go\n", "import pybamm\n", "from scipy.io import loadmat\n", "\n", "import pybop" ] }, { "cell_type": "markdown", "id": "a976f817-f0b3-421e-8cd3-a49be9128068", "metadata": {}, "source": [ "## Importing Data\n", "\n", "The data is imported as a dictionary with the following key level:\n", "- [\"LGM50_5Ah_Pulse\"]\n", " - Temperature-> [\"T0\"]\n", " - State of Charge ->[\"SoC3\"]\n", " - Cell number -> [\"Cell1\"]\n", " - Corresponding data -> [\"data\"]\n", "\n", "Using SciPy's `loadmat`, we import the data from the MAT containers:" ] }, { "cell_type": "code", "execution_count": 3, "id": "705e7986", "metadata": { "execution": { "iopub.execute_input": "2024-04-14T18:57:46.250744Z", "iopub.status.busy": "2024-04-14T18:57:46.250383Z", "iopub.status.idle": "2024-04-14T18:57:46.294482Z", "shell.execute_reply": "2024-04-14T18:57:46.294078Z" } }, "outputs": [], "source": [ "ocp = loadmat(\"data/LGM50_5Ah_OCV.mat\", simplify_cells=True, mat_dtype=False)\n", "pulse_data = loadmat(\"data/LGM50_5Ah_Pulse.mat\", simplify_cells=True, mat_dtype=False)\n", "rate_data = loadmat(\"data/LGM50_5Ah_RateTest.mat\", simplify_cells=True, mat_dtype=False)" ] }, { "cell_type": "markdown", "id": "609b0fc7", "metadata": {}, "source": [ "### Convert to Dataframes\n", "\n", "Next, we construct a dataframe from a selected pulse. In this case, we select the data for zero degrees (`T0`) with a state-of-charge of 90% (`SoC9`) and the 19th cell (`Cell19`). This can be extended to multiple pulses, or a different selection.\n", "\n", "Additionally, we apply two filters to the dataframe to ensure the data contains only monotonically increasing time samples without duplicates." ] }, { "cell_type": "code", "execution_count": 4, "id": "cc48c662", "metadata": { "execution": { "iopub.execute_input": "2024-04-14T18:57:46.296068Z", "iopub.status.busy": "2024-04-14T18:57:46.295926Z", "iopub.status.idle": "2024-04-14T18:57:46.302754Z", "shell.execute_reply": "2024-04-14T18:57:46.302555Z" } }, "outputs": [], "source": [ "df = pd.DataFrame(pulse_data[\"LGM50_5Ah_Pulse\"][\"T0\"][\"SoC9\"][\"Cell19\"][\"data\"])\n", "df[\"ProgTime\"] = df[\"ProgTime\"] - df[\"ProgTime\"].min()\n", "df.drop_duplicates(subset=[\"ProgTime\"], inplace=True)" ] }, { "cell_type": "markdown", "id": "34aeb1d2", "metadata": {}, "source": [ "A plot of time vs voltage confirms the data looks correct for fitting. In this situation, we would prefer to have additional samples from the relaxation, but as we will show below, PyBOP is still able to identify parameter values that fit this system." ] }, { "cell_type": "code", "execution_count": 5, "id": "c4189ca7", "metadata": { "execution": { "iopub.execute_input": "2024-04-14T18:57:46.304020Z", "iopub.status.busy": "2024-04-14T18:57:46.303922Z", "iopub.status.idle": "2024-04-14T18:57:46.726277Z", "shell.execute_reply": "2024-04-14T18:57:46.725777Z" } }, "outputs": [ { "data": { "text/html": [ " \n", " " ] }, "metadata": {}, "output_type": "display_data" }, { "data": { "application/vnd.plotly.v1+json": { "config": { "plotlyServerURL": "https://plot.ly" }, "data": [ { "type": "scatter", "x": [ 0.0, 0.01800000004004687, 0.12100000004284084, 0.25100000004749745, 0.34300000010989606, 0.4190000001108274, 0.5600000000558794, 0.6170000000856817, 0.7250000000931323, 0.8570000000763685, 0.9250000000465661, 1.0330000000540167, 1.1739999999990687, 1.2300000000977889, 1.343000000109896, 1.4170000000158325, 1.5370000000111759, 1.6480000000447035, 1.7160000000149012, 1.8209999999962747, 1.922000000020489, 2.0010000000474975, 2.1510000000707805, 2.2290000000502914, 2.4300000000512227, 2.4980000000214204, 2.534000000101514, 2.7020000000484288, 2.7989999999990687, 2.8380000001052395, 3.002000000094995, 3.103000000002794, 3.1440000000875443, 3.2660000000614673, 3.3570000000763685, 3.4860000000335276, 3.525000000023283, 3.7220000000670552, 3.762000000104308, 3.8320000000530854, 4.0230000000447035, 4.069000000017695, 4.14000000001397, 4.282000000006519, 4.3600000001024455, 4.44800000009127, 4.5070000000996515, 4.633000000030734, 4.726000000024214, 4.94800000009127, 4.990000000107102, 5.033000000054017, 5.134000000078231, 5.24800000002142, 5.339000000036322, 5.474000000045635, 5.57300000009127, 5.614000000059605, 5.7570000000996515, 5.875, 5.926000000094064, 6.0670000000391155, 6.182000000029802, 6.2350000001024455, 6.341000000014901, 6.512000000104308, 6.579000000027008, 6.618000000016764, 6.7730000000447035, 6.856000000028871, 6.927000000025146, 7.066000000108033, 7.1510000000707805, 7.238000000012107, 7.3080000000773, 7.4610000000102445, 7.546000000089407, 7.753000000026077, 7.815000000060536, 7.853000000002794, 7.923999999999069, 8.051000000094064, 8.160000000032596, 8.23300000000745, 8.318000000086613, 8.427000000025146, 8.53900000010617, 8.660000000032596, 8.747000000090338, 8.852000000071712, 8.989000000059605, 9.078000000095926, 9.127000000094995, 9.274000000092201, 9.361000000033528, 9.434000000008382, 9.524000000092201, 9.63600000005681, 9.754000000073574, 9.83800000010524, 9.949000000022352, 10.016000000061467, 10.065000000060536, 10.085000000079162, 11.104000000050291, 12.092000000062399, 13.12100000004284, 14.091000000014901, 15.08800000010524, 16.113000000012107, 17.14000000001397, 18.087000000057742, 19.101000000024214, 20.10800000000745 ], "y": [ 4.08078, 3.96745, 3.96156, 3.96156, 3.95955, 3.959, 3.95889, 3.95855, 3.95755, 3.95755, 3.95722, 3.95644, 3.95644, 3.95611, 3.95533, 3.95511, 3.95511, 3.95433, 3.95422, 3.95422, 3.95355, 3.95333, 3.95322, 3.95266, 3.95255, 3.95221, 3.95188, 3.95166, 3.95166, 3.95121, 3.95099, 3.95088, 3.95055, 3.95032, 3.9501, 3.94999, 3.94977, 3.94955, 3.94932, 3.9491, 3.94888, 3.94866, 3.94843, 3.94832, 3.9481, 3.94788, 3.94777, 3.94766, 3.94743, 3.9471, 3.94699, 3.94677, 3.94665, 3.94665, 3.94621, 3.9461, 3.9461, 3.94588, 3.94565, 3.94554, 3.94532, 3.94521, 3.9451, 3.94488, 3.94476, 3.94454, 3.94443, 3.94421, 3.9441, 3.94399, 3.94376, 3.94365, 3.94354, 3.94332, 3.94321, 3.94321, 3.94287, 3.94276, 3.94265, 3.94243, 3.94232, 3.94221, 3.9421, 3.94187, 3.94176, 3.94176, 3.94154, 3.94143, 3.94132, 3.9411, 3.94098, 3.94087, 3.94076, 3.94054, 3.94054, 3.94043, 3.94021, 3.94021, 3.93998, 3.93987, 3.93987, 3.93976, 3.93954, 3.93943, 4.06199, 4.06411, 4.06544, 4.06644, 4.06744, 4.06822, 4.06878, 4.06922, 4.06978, 4.07011 ] } ], "layout": { "template": { "data": { "bar": [ { "error_x": { "color": "#2a3f5f" }, "error_y": { "color": "#2a3f5f" }, "marker": { "line": { "color": "#E5ECF6", "width": 0.5 }, "pattern": { "fillmode": "overlay", "size": 10, "solidity": 0.2 } }, "type": "bar" } ], "barpolar": [ { "marker": { "line": { "color": "#E5ECF6", "width": 0.5 }, "pattern": { "fillmode": "overlay", "size": 10, "solidity": 0.2 } }, "type": "barpolar" } ], "carpet": [ { "aaxis": { "endlinecolor": "#2a3f5f", "gridcolor": "white", "linecolor": "white", "minorgridcolor": "white", "startlinecolor": "#2a3f5f" }, "baxis": { "endlinecolor": "#2a3f5f", "gridcolor": "white", "linecolor": "white", "minorgridcolor": "white", "startlinecolor": "#2a3f5f" }, "type": "carpet" } ], "choropleth": [ { "colorbar": { "outlinewidth": 0, "ticks": "" }, "type": "choropleth" } ], "contour": [ { "colorbar": { "outlinewidth": 0, "ticks": "" }, "colorscale": [ [ 0.0, "#0d0887" ], [ 0.1111111111111111, "#46039f" ], [ 0.2222222222222222, "#7201a8" ], [ 0.3333333333333333, "#9c179e" ], [ 0.4444444444444444, "#bd3786" ], [ 0.5555555555555556, "#d8576b" ], [ 0.6666666666666666, "#ed7953" ], [ 0.7777777777777778, "#fb9f3a" ], [ 0.8888888888888888, "#fdca26" ], [ 1.0, "#f0f921" ] ], "type": "contour" } ], "contourcarpet": [ { "colorbar": { "outlinewidth": 0, "ticks": "" }, "type": "contourcarpet" } ], "heatmap": [ { "colorbar": { "outlinewidth": 0, "ticks": "" }, "colorscale": [ [ 0.0, "#0d0887" ], [ 0.1111111111111111, "#46039f" ], [ 0.2222222222222222, "#7201a8" ], [ 0.3333333333333333, "#9c179e" ], [ 0.4444444444444444, "#bd3786" ], [ 0.5555555555555556, "#d8576b" ], [ 0.6666666666666666, "#ed7953" ], [ 0.7777777777777778, "#fb9f3a" ], [ 0.8888888888888888, "#fdca26" ], [ 1.0, "#f0f921" ] ], "type": "heatmap" } ], "heatmapgl": [ { "colorbar": { "outlinewidth": 0, "ticks": "" }, "colorscale": [ [ 0.0, "#0d0887" ], [ 0.1111111111111111, "#46039f" ], [ 0.2222222222222222, "#7201a8" ], [ 0.3333333333333333, "#9c179e" ], [ 0.4444444444444444, "#bd3786" ], [ 0.5555555555555556, "#d8576b" ], [ 0.6666666666666666, "#ed7953" ], [ 0.7777777777777778, "#fb9f3a" ], [ 0.8888888888888888, "#fdca26" ], [ 1.0, "#f0f921" ] ], "type": "heatmapgl" } ], "histogram": [ { "marker": { "pattern": { "fillmode": "overlay", "size": 10, "solidity": 0.2 } }, "type": "histogram" } ], "histogram2d": [ { "colorbar": { "outlinewidth": 0, "ticks": "" }, "colorscale": [ [ 0.0, "#0d0887" ], [ 0.1111111111111111, "#46039f" ], [ 0.2222222222222222, "#7201a8" ], [ 0.3333333333333333, "#9c179e" ], [ 0.4444444444444444, "#bd3786" ], [ 0.5555555555555556, "#d8576b" ], [ 0.6666666666666666, "#ed7953" ], [ 0.7777777777777778, "#fb9f3a" ], [ 0.8888888888888888, "#fdca26" ], [ 1.0, "#f0f921" ] ], "type": "histogram2d" } ], "histogram2dcontour": [ { "colorbar": { "outlinewidth": 0, "ticks": "" }, "colorscale": [ [ 0.0, "#0d0887" ], [ 0.1111111111111111, "#46039f" ], [ 0.2222222222222222, "#7201a8" ], [ 0.3333333333333333, "#9c179e" ], [ 0.4444444444444444, "#bd3786" ], [ 0.5555555555555556, "#d8576b" ], [ 0.6666666666666666, "#ed7953" ], [ 0.7777777777777778, "#fb9f3a" ], [ 0.8888888888888888, "#fdca26" ], [ 1.0, "#f0f921" ] ], "type": "histogram2dcontour" } ], "mesh3d": [ { "colorbar": { "outlinewidth": 0, "ticks": "" }, "type": "mesh3d" } ], "parcoords": [ { "line": { "colorbar": { "outlinewidth": 0, "ticks": "" } }, "type": "parcoords" } ], "pie": [ { "automargin": true, "type": "pie" } ], "scatter": [ { "fillpattern": { "fillmode": "overlay", "size": 10, "solidity": 0.2 }, "type": "scatter" } ], "scatter3d": [ { "line": { "colorbar": { "outlinewidth": 0, "ticks": "" } }, "marker": { "colorbar": { "outlinewidth": 0, "ticks": "" } }, "type": "scatter3d" } ], "scattercarpet": [ { "marker": { "colorbar": { "outlinewidth": 0, "ticks": "" } }, "type": "scattercarpet" } ], "scattergeo": [ { "marker": { "colorbar": { "outlinewidth": 0, "ticks": "" } }, "type": "scattergeo" } ], "scattergl": [ { "marker": { "colorbar": { "outlinewidth": 0, "ticks": "" } }, "type": "scattergl" } ], "scattermapbox": [ { "marker": { "colorbar": { "outlinewidth": 0, "ticks": "" } }, "type": "scattermapbox" } ], "scatterpolar": [ { "marker": { "colorbar": { "outlinewidth": 0, "ticks": "" } }, "type": "scatterpolar" } ], "scatterpolargl": [ { "marker": { "colorbar": { "outlinewidth": 0, "ticks": "" } }, "type": "scatterpolargl" } ], "scatterternary": [ { "marker": { "colorbar": { "outlinewidth": 0, "ticks": "" } }, "type": "scatterternary" } ], "surface": [ { "colorbar": { "outlinewidth": 0, "ticks": "" }, "colorscale": [ [ 0.0, "#0d0887" ], [ 0.1111111111111111, "#46039f" ], [ 0.2222222222222222, "#7201a8" ], [ 0.3333333333333333, "#9c179e" ], [ 0.4444444444444444, "#bd3786" ], [ 0.5555555555555556, "#d8576b" ], [ 0.6666666666666666, "#ed7953" ], [ 0.7777777777777778, "#fb9f3a" ], [ 0.8888888888888888, "#fdca26" ], [ 1.0, "#f0f921" ] ], "type": "surface" } ], "table": [ { "cells": { "fill": { "color": "#EBF0F8" }, "line": { "color": "white" } }, "header": { "fill": { "color": "#C8D4E3" }, "line": { "color": "white" } }, "type": "table" } ] }, "layout": { "annotationdefaults": { "arrowcolor": "#2a3f5f", "arrowhead": 0, "arrowwidth": 1 }, "autotypenumbers": "strict", "coloraxis": { "colorbar": { "outlinewidth": 0, "ticks": "" } }, "colorscale": { "diverging": [ [ 0, "#8e0152" ], [ 0.1, "#c51b7d" ], [ 0.2, "#de77ae" ], [ 0.3, "#f1b6da" ], [ 0.4, "#fde0ef" ], [ 0.5, "#f7f7f7" ], [ 0.6, "#e6f5d0" ], [ 0.7, "#b8e186" ], [ 0.8, "#7fbc41" ], [ 0.9, "#4d9221" ], [ 1, "#276419" ] ], "sequential": [ [ 0.0, "#0d0887" ], [ 0.1111111111111111, "#46039f" ], [ 0.2222222222222222, "#7201a8" ], [ 0.3333333333333333, "#9c179e" ], [ 0.4444444444444444, "#bd3786" ], [ 0.5555555555555556, "#d8576b" ], [ 0.6666666666666666, "#ed7953" ], [ 0.7777777777777778, "#fb9f3a" ], [ 0.8888888888888888, "#fdca26" ], [ 1.0, "#f0f921" ] ], "sequentialminus": [ [ 0.0, "#0d0887" ], [ 0.1111111111111111, "#46039f" ], [ 0.2222222222222222, "#7201a8" ], [ 0.3333333333333333, "#9c179e" ], [ 0.4444444444444444, "#bd3786" ], [ 0.5555555555555556, "#d8576b" ], [ 0.6666666666666666, "#ed7953" ], [ 0.7777777777777778, "#fb9f3a" ], [ 0.8888888888888888, "#fdca26" ], [ 1.0, "#f0f921" ] ] }, "colorway": [ "#636efa", "#EF553B", "#00cc96", "#ab63fa", "#FFA15A", "#19d3f3", "#FF6692", "#B6E880", "#FF97FF", "#FECB52" ], "font": { "color": "#2a3f5f" }, "geo": { "bgcolor": "white", "lakecolor": "white", "landcolor": "#E5ECF6", "showlakes": true, "showland": true, "subunitcolor": "white" }, "hoverlabel": { "align": "left" }, "hovermode": "closest", "mapbox": { "style": "light" }, "paper_bgcolor": "white", "plot_bgcolor": "#E5ECF6", "polar": { "angularaxis": { "gridcolor": "white", "linecolor": "white", "ticks": "" }, "bgcolor": "#E5ECF6", "radialaxis": { "gridcolor": "white", "linecolor": "white", "ticks": "" } }, "scene": { "xaxis": { "backgroundcolor": "#E5ECF6", "gridcolor": "white", "gridwidth": 2, "linecolor": "white", "showbackground": true, "ticks": "", "zerolinecolor": "white" }, "yaxis": { "backgroundcolor": "#E5ECF6", "gridcolor": "white", "gridwidth": 2, "linecolor": "white", "showbackground": true, "ticks": "", "zerolinecolor": "white" }, "zaxis": { "backgroundcolor": "#E5ECF6", "gridcolor": "white", "gridwidth": 2, "linecolor": "white", "showbackground": true, "ticks": "", "zerolinecolor": "white" } }, "shapedefaults": { "line": { "color": "#2a3f5f" } }, "ternary": { "aaxis": { "gridcolor": "white", "linecolor": "white", "ticks": "" }, "baxis": { "gridcolor": "white", "linecolor": "white", "ticks": "" }, "bgcolor": "#E5ECF6", "caxis": { "gridcolor": "white", "linecolor": "white", "ticks": "" } }, "title": { "x": 0.05 }, "xaxis": { "automargin": true, "gridcolor": "white", "linecolor": "white", "ticks": "", "title": { "standoff": 15 }, "zerolinecolor": "white", "zerolinewidth": 2 }, "yaxis": { "automargin": true, "gridcolor": "white", "linecolor": "white", "ticks": "", "title": { "standoff": 15 }, "zerolinecolor": "white", "zerolinewidth": 2 } } } } }, "text/html": [ "