Widget:Solvency2 BalanceSheet
Solvency II Balance Sheet
Adjust the sliders to explore how changes in assets and liabilities affect the solvency position.
<svg class="s2-ratio-ring" viewBox="0 0 120 120">
<circle class="s2-ring-bg" cx="60" cy="60" r="52" />
<circle class="s2-ring-fg" cx="60" cy="60" r="52" stroke-dasharray="326.73" stroke-dashoffset="326.73" />
</svg>
0% Solvency Ratio
SCR Coverage: — MCR Coverage: —
Assets
Liabilities & Own Funds
<fieldset class="s2-fieldset">
<legend>Assets</legend>
</fieldset>
<fieldset class="s2-fieldset">
<legend>Liabilities</legend>
</fieldset>
</thead> <tbody id="s2-summary-tbody"></tbody>
| Item | Value | Category |
|---|
This module is for educational purposes only and uses simplified, illustrative figures. Actual Solvency II reporting follows EIOPA technical standards.
<style> /* ===== STRICT SCOPING — every rule prefixed ===== */
- insurerbrain-module-solvency2 {
--s2-accent: #1a6b4e; --s2-accent-light: #e3f2ec; --s2-warn: #c0760a; --s2-warn-light: #fdf3e1; --s2-danger: #b52a2a; --s2-danger-light: #fce8e8; --s2-border: #c8ccd1; --s2-text: #202122; --s2-text-muted: #54595d; --s2-surface: #f8f9fa; --s2-white: #ffffff; --s2-radius: 0.35rem; max-width: 64rem; margin: 1.5rem auto; padding: 0 0.75rem;
}
/* ---- Header ---- */
- insurerbrain-module-solvency2 .s2-header {
margin-bottom: 1.25rem;
}
- insurerbrain-module-solvency2 .s2-title {
margin: 0 0 0.25rem; border-bottom: none;
}
- insurerbrain-module-solvency2 .s2-subtitle {
margin: 0; color: var(--s2-text-muted);
}
/* ---- Dashboard ---- */
- insurerbrain-module-solvency2 .s2-dashboard {
display: flex; gap: 1.25rem; flex-wrap: wrap; margin-bottom: 1.5rem;
}
/* -- Ratio Panel -- */
- insurerbrain-module-solvency2 .s2-ratio-panel {
flex: 0 0 auto; min-width: 11rem; display: flex; flex-direction: column; align-items: center; gap: 0.6rem; padding: 1rem; border: 1px solid var(--s2-border); border-radius: var(--s2-radius); background: var(--s2-surface);
}
- insurerbrain-module-solvency2 .s2-ratio-ring-wrap {
position: relative; width: 7.5rem; height: 7.5rem;
}
- insurerbrain-module-solvency2 .s2-ratio-ring {
width: 100%; height: 100%; transform: rotate(-90deg);
}
- insurerbrain-module-solvency2 .s2-ring-bg {
fill: none; stroke: var(--s2-border); stroke-width: 8;
}
- insurerbrain-module-solvency2 .s2-ring-fg {
fill: none; stroke: var(--s2-accent); stroke-width: 8; stroke-linecap: round; transition: stroke-dashoffset 0.5s ease, stroke 0.4s ease;
}
- insurerbrain-module-solvency2 .s2-ratio-label {
position: absolute; inset: 0; display: flex; flex-direction: column; align-items: center; justify-content: center;
}
- insurerbrain-module-solvency2 .s2-ratio-value {
font-size: 1.5rem; font-weight: 700; line-height: 1.1; color: var(--s2-text);
}
- insurerbrain-module-solvency2 .s2-ratio-caption {
font-size: 0.7rem; text-transform: uppercase; letter-spacing: 0.04em; color: var(--s2-text-muted);
}
- insurerbrain-module-solvency2 .s2-ratio-badges {
display: flex; flex-wrap: wrap; gap: 0.35rem; justify-content: center;
}
- insurerbrain-module-solvency2 .s2-badge {
font-size: 0.72rem; padding: 0.15rem 0.45rem; border-radius: 999px; background: var(--s2-accent-light); color: var(--s2-accent); white-space: nowrap;
}
- insurerbrain-module-solvency2 .s2-status-bar {
font-size: 0.78rem; font-weight: 600; padding: 0.3rem 0.7rem; border-radius: var(--s2-radius); text-align: center; transition: background 0.3s, color 0.3s;
}
/* -- Balance Sheet Columns -- */
- insurerbrain-module-solvency2 .s2-sheet-wrap {
flex: 1 1 20rem; display: flex; gap: 0.5rem; min-height: 18rem;
}
- insurerbrain-module-solvency2 .s2-col {
flex: 1; display: flex; flex-direction: column; border: 1px solid var(--s2-border); border-radius: var(--s2-radius); overflow: hidden; background: var(--s2-white);
}
- insurerbrain-module-solvency2 .s2-col-head {
margin: 0; padding: 0.45rem 0.6rem; font-size: 0.82rem; text-transform: uppercase; letter-spacing: 0.04em; border-bottom: 1px solid var(--s2-border); background: var(--s2-surface);
}
- insurerbrain-module-solvency2 .s2-bar-stack {
flex: 1; display: flex; flex-direction: column; padding: 0.25rem; gap: 2px;
}
- insurerbrain-module-solvency2 .s2-bar-item {
display: flex; align-items: center; justify-content: space-between; padding: 0.25rem 0.45rem; border-radius: 3px; font-size: 0.75rem; color: var(--s2-white); transition: flex-grow 0.45s ease; overflow: hidden; min-height: 1.4rem;
}
- insurerbrain-module-solvency2 .s2-bar-item span:last-child {
font-weight: 600; margin-left: 0.3rem; white-space: nowrap;
}
- insurerbrain-module-solvency2 .s2-col-total {
padding: 0.35rem 0.6rem; font-size: 0.82rem; border-top: 1px solid var(--s2-border); background: var(--s2-surface); text-align: right;
}
/* ---- Controls ---- */
- insurerbrain-module-solvency2 .s2-controls {
display: flex; gap: 1rem; flex-wrap: wrap; margin-bottom: 1.25rem;
}
- insurerbrain-module-solvency2 .s2-fieldset {
flex: 1 1 18rem; border: 1px solid var(--s2-border); border-radius: var(--s2-radius); padding: 0.6rem 0.8rem 0.8rem; margin: 0; background: var(--s2-surface);
}
- insurerbrain-module-solvency2 .s2-fieldset legend {
font-weight: 600; font-size: 0.85rem; padding: 0 0.3rem;
}
- insurerbrain-module-solvency2 .s2-slider-grid {
display: grid; grid-template-columns: repeat(auto-fill, minmax(13rem, 1fr)); gap: 0.55rem;
}
- insurerbrain-module-solvency2 .s2-slider-group {
display: flex; flex-direction: column; gap: 0.15rem;
}
- insurerbrain-module-solvency2 .s2-slider-label {
display: flex; justify-content: space-between; font-size: 0.78rem; color: var(--s2-text-muted);
}
- insurerbrain-module-solvency2 .s2-slider-label strong {
color: var(--s2-text);
}
- insurerbrain-module-solvency2 .s2-slider-group input[type="range"] {
width: 100%; cursor: pointer; accent-color: var(--s2-accent);
}
/* ---- Summary Table ---- */
- insurerbrain-module-solvency2 .s2-summary-table {
width: 100%; margin-top: 0;
}
/* ---- Footnote ---- */
- insurerbrain-module-solvency2 .s2-footnote {
font-size: 0.78rem; color: var(--s2-text-muted); margin-top: 0.5rem;
}
/* ---- Status colours ---- */
- insurerbrain-module-solvency2 .s2-status-good {
background: var(--s2-accent-light); color: var(--s2-accent);
}
- insurerbrain-module-solvency2 .s2-status-warn {
background: var(--s2-warn-light); color: var(--s2-warn);
}
- insurerbrain-module-solvency2 .s2-status-danger {
background: var(--s2-danger-light); color: var(--s2-danger);
}
/* ---- Responsive ---- */ @media (max-width: 48rem) {
#insurerbrain-module-solvency2 .s2-dashboard {
flex-direction: column;
}
#insurerbrain-module-solvency2 .s2-ratio-panel {
flex-direction: row;
flex-wrap: wrap;
justify-content: center;
}
#insurerbrain-module-solvency2 .s2-sheet-wrap {
min-height: 14rem;
}
} </style>
<script> (function () {
'use strict';
/* ============ DATA MODEL ============ */
var assetItems = [
{ key: 'gov_bonds', label: 'Government Bonds', value: 350, min: 0, max: 800, color: '#1a6b4e' },
{ key: 'corp_bonds', label: 'Corporate Bonds', value: 220, min: 0, max: 600, color: '#2a8c68' },
{ key: 'equities', label: 'Equities', value: 120, min: 0, max: 400, color: '#3bae85' },
{ key: 'property', label: 'Property', value: 80, min: 0, max: 300, color: '#5bc4a0' },
{ key: 'reins_recv', label: 'Reinsurance Recoverables',value: 60, min: 0, max: 200, color: '#85d4b8' },
{ key: 'cash', label: 'Cash & Equivalents', value: 40, min: 0, max: 200, color: '#abd9c9' }
];
var liabilityItems = [
{ key: 'best_est', label: 'Best Estimate Liabilities', value: 480, min: 100, max: 900, color: '#8b3a3a' },
{ key: 'risk_margin', label: 'Risk Margin', value: 45, min: 5, max: 150, color: '#b35656' },
{ key: 'other_liab', label: 'Other Liabilities', value: 55, min: 0, max: 200, color: '#cc8080' },
{ key: 'scr', label: 'SCR (Own Funds Buffer)', value: 180, min: 20, max: 400, color: '#1b5e90' },
{ key: 'mcr', label: 'MCR (Minimum Capital)', value: 70, min: 10, max: 200, color: '#3a8bc2' }
];
/* ============ REFERENCES ============ */
var root = document.getElementById('insurerbrain-module-solvency2');
var assetSliders = root.querySelector('#s2-asset-sliders');
var liabSliders = root.querySelector('#s2-liability-sliders');
var assetBars = root.querySelector('#s2-asset-bars');
var liabBars = root.querySelector('#s2-liability-bars');
var assetTotalEl = root.querySelector('#s2-asset-total');
var liabTotalEl = root.querySelector('#s2-liability-total');
var ratioValueEl = root.querySelector('#s2-ratio-value');
var ringFg = root.querySelector('.s2-ring-fg');
var statusBar = root.querySelector('#s2-status-bar');
var badgeSCR = root.querySelector('#s2-badge-scr');
var badgeMCR = root.querySelector('#s2-badge-mcr');
var tbody = root.querySelector('#s2-summary-tbody');
var CIRCUMFERENCE = 2 * Math.PI * 52; // matches r=52
/* ============ BUILD SLIDERS ============ */
function buildSliders(items, container) {
items.forEach(function (item) {
var group = document.createElement('div');
group.className = 's2-slider-group';
var lbl = document.createElement('div');
lbl.className = 's2-slider-label';
lbl.innerHTML = '' + item.label + '' + item.value + '';
var inp = document.createElement('input');
inp.type = 'range';
inp.min = item.min;
inp.max = item.max;
inp.value = item.value;
inp.id = 's2-range-' + item.key;
inp.setAttribute('aria-label', item.label + ' (€m)');
inp.addEventListener('input', function () {
item.value = Number(this.value);
root.querySelector('#s2-val-' + item.key).textContent = item.value;
update();
});
group.appendChild(lbl);
group.appendChild(inp);
container.appendChild(group);
});
}
/* ============ BUILD BAR ITEMS (once) ============ */
function buildBars(items, container) {
items.forEach(function (item) {
var bar = document.createElement('div');
bar.className = 's2-bar-item';
bar.id = 's2-bar-' + item.key;
bar.style.background = item.color;
bar.innerHTML = '' + item.label + '';
container.appendChild(bar);
});
}
/* ============ UPDATE ============ */
function update() {
var totalAssets = assetItems.reduce(function (s, i) { return s + i.value; }, 0);
var techProv = liabilityItems[0].value + liabilityItems[1].value; // BE + RM
var otherLiab = liabilityItems[2].value;
var scrReq = liabilityItems[3].value;
var mcrReq = liabilityItems[4].value;
var totalLiabSide = techProv + otherLiab + scrReq + mcrReq;
// Eligible Own Funds = Assets - Technical Provisions - Other Liabilities var eof = totalAssets - techProv - otherLiab; if (eof < 0) eof = 0;
var solvencyRatio = scrReq > 0 ? (eof / scrReq) * 100 : 0; var mcrRatio = mcrReq > 0 ? (eof / mcrReq) * 100 : 0;
// Ratio ring var capped = Math.min(solvencyRatio, 250); var offset = CIRCUMFERENCE - (CIRCUMFERENCE * capped / 250); ringFg.style.strokeDashoffset = offset;
var ringColor; if (solvencyRatio >= 150) ringColor = '#1a6b4e'; else if (solvencyRatio >= 100) ringColor = '#c0760a'; else ringColor = '#b52a2a'; ringFg.style.stroke = ringColor;
ratioValueEl.textContent = Math.round(solvencyRatio) + '%';
badgeSCR.textContent = 'SCR Coverage: ' + Math.round(solvencyRatio) + '%'; badgeMCR.textContent = 'MCR Coverage: ' + Math.round(mcrRatio) + '%';
// Status
statusBar.classList.remove('s2-status-good', 's2-status-warn', 's2-status-danger');
if (solvencyRatio >= 150) {
statusBar.textContent = 'Comfortable — well above SCR';
statusBar.classList.add('s2-status-good');
} else if (solvencyRatio >= 100) {
statusBar.textContent = 'Caution — approaching SCR threshold';
statusBar.classList.add('s2-status-warn');
} else {
statusBar.textContent = 'Breach — own funds below SCR';
statusBar.classList.add('s2-status-danger');
}
// Asset bars
assetItems.forEach(function (item) {
var bar = root.querySelector('#s2-bar-' + item.key);
bar.style.flexGrow = item.value || 0.01;
bar.querySelector('span:last-child').textContent = item.value + ' €m';
});
assetTotalEl.textContent = totalAssets;
// Liability bars
liabilityItems.forEach(function (item) {
var bar = root.querySelector('#s2-bar-' + item.key);
bar.style.flexGrow = item.value || 0.01;
bar.querySelector('span:last-child').textContent = item.value + ' €m';
});
liabTotalEl.textContent = totalLiabSide;
// Summary table
var rows = [];
assetItems.forEach(function (i) { rows.push([i.label, i.value, 'Asset']); });
rows.push(['Total Assets', '' + totalAssets + '', ]);
liabilityItems.forEach(function (i) { rows.push([i.label, i.value, 'Liability / Capital']); });
rows.push(['Technical Provisions', '' + techProv + '', ]);
rows.push(['Eligible Own Funds', '' + Math.round(eof) + '', ]);
rows.push(['Solvency Ratio (EOF / SCR)', '' + Math.round(solvencyRatio) + '%', ]);
tbody.innerHTML = rows.map(function (r) {
return '' + r[0] + '' + r[1] + '' + r[2] + '';
}).join(); }
/* ============ INIT ============ */ buildSliders(assetItems, assetSliders); buildSliders(liabilityItems, liabSliders); buildBars(assetItems, assetBars); buildBars(liabilityItems, liabBars); update();
})(); </script>