Skip to content
Snippets Groups Projects
Unverified Commit 231b0a85 authored by Dorine Lambinet's avatar Dorine Lambinet
Browse files

Supprime ancien composant PaySlipCompareViewOld

parent 0f050f55
No related branches found
No related tags found
1 merge request!302Resolve "Appliquer la nouvelle feuille de paie au mode comparaison"
Pipeline #19991 passed
<script lang="ts">
import { preventDefault } from "svelte/legacy"
import type { VariableByName } from "@openfisca/json-model"
import { goto } from "$app/navigation"
import { page } from "$app/stores"
import Tooltip from "$lib/components/ui_transverse_components/Tooltip.svelte"
import type {
EvaluationByName,
VisibleDecompositionForComparison,
} from "$lib/decompositions"
import { buildVisibleDecompositionsForComparison } from "$lib/decompositions"
import type { DisplayMode } from "$lib/displays"
import { entityByKey } from "$lib/entities"
import { shared } from "$lib/shared.svelte"
import type { Situation } from "$lib/situations"
import { newSimulationUrl } from "$lib/urls"
import { removeNegativeZero } from "$lib/values"
interface Props {
displayMode: DisplayMode
evaluationByNameArray: EvaluationByName[]
situations: Situation[]
situationsToCompareIndex: number[]
showLoader?: boolean
variableSummaryByName: VariableByName
year: number
}
let {
displayMode,
evaluationByNameArray,
situations,
situationsToCompareIndex,
showLoader = true,
variableSummaryByName,
year,
}: Props = $props()
const dateFormatter = new Intl.DateTimeFormat("fr-FR", { dateStyle: "full" })
.format
const deltaFormatter = (value: number): string =>
new Intl.NumberFormat("fr-FR", {
currency: "EUR",
maximumFractionDigits: 0,
minimumFractionDigits: 0,
signDisplay: "never",
style: "currency",
}).format(removeNegativeZero(value))
let useRevaluationInsteadOfLaw = $derived(
$page.data.revaluationName !== undefined,
)
let firstCalculationName = $derived(
useRevaluationInsteadOfLaw ? "revaluation" : "law",
)
let runningCalculationNames = $derived(
Object.entries(shared.calculationByName)
.filter(([, calculation]) => calculation.running)
.map(([calculationName]) => calculationName),
)
let modificationsAmendmentCount = $derived(
Object.keys(shared.parametricReform).length,
)
let visibleDecompositions: VisibleDecompositionForComparison[] = $state([])
$effect(() => {
visibleDecompositions = buildVisibleDecompositionsForComparison(
shared.decompositionByName,
entityByKey,
situationsToCompareIndex.map(
(situationIndex) => evaluationByNameArray[situationIndex],
),
situationsToCompareIndex.map(
(situationIndex) => situations[situationIndex],
),
variableSummaryByName,
shared.waterfall,
shared.showNulls,
useRevaluationInsteadOfLaw,
shared.vectorLength,
year,
)
})
function* iterToDepth(depth: number): Generator<number, void, unknown> {
for (let i = 0; i < depth; i++) {
yield i
}
}
function zoomIn(index: number) {
let visibleDecomposition = visibleDecompositions[index]
if (
visibleDecomposition === undefined ||
visibleDecomposition.visibleChildren === undefined
) {
return
}
let decomposition = visibleDecomposition.decomposition
if (!decomposition.open) {
shared.decompositionByName[decomposition.name] = {
...decomposition,
open: true,
}
return
}
}
function zoomOut(index: number) {
let visibleDecomposition = visibleDecompositions[index]
if (
visibleDecomposition === undefined ||
visibleDecomposition.visibleChildren === undefined
) {
return
}
let decomposition = visibleDecomposition.decomposition
if (decomposition.open) {
shared.decompositionByName[decomposition.name] = {
...decomposition,
open: false,
}
return
}
}
</script>
{#if visibleDecompositions.length > 0}
<div>
<div class="h-5 bg-gradient-to-b from-gray-100 to-transparent" />
<!--Montants-nuls-->
<div class="mx-1 mb-3 flex justify-start">
<label class="inline-flex cursor-pointer items-center">
<input
type="checkbox"
value=""
class="peer sr-only"
bind:checked={shared.showNulls}
/>
<div
class="peer relative h-6 w-11 shrink-0 rounded-full bg-gray-400 after:absolute after:start-[2px] after:top-[2px] after:h-5 after:w-5 after:rounded-full after:bg-white after:transition-all after:content-[''] peer-checked:bg-le-bleu peer-checked:after:translate-x-full peer-checked:after:border-white peer-focus:outline-none peer-focus:ring-0"
></div>
<span class="ms-3 text-sm font-medium text-gray-900 dark:text-gray-300"
>Montrer tous les dispositifs, y compris si leur montant est à 0€.</span
>
</label>
</div>
</div>
<!-- Labels and compared amounts of decompositions -->
<div>
{#each visibleDecompositions as { decomposition, depth, rows, trunk, visibleChildren }, index}
<!-- Decomposition label -->
<div class="flex h-7 items-center whitespace-nowrap">
{#if trunk}
<div
class="ml-2 mt-2 w-full overflow-x-hidden text-ellipsis border-gray-300 text-left text-base text-gray-500 hover:z-20 hover:overflow-x-visible"
class:border-t={index !== 0}
>
{#if displayMode.edit !== undefined}
<!-- Trunk decomposition node, in variable inputs mode => link -->
<a
class="cursor-pointer text-base hover:underline"
href={newSimulationUrl({
...displayMode,
variableName: decomposition.name,
})}
data-sveltekit-noscroll
>{decomposition.short_label ?? decomposition.label}</a
>
{:else}
<!-- Trunk decomposition node with parameters, in parameters mode => link -->
<a
class="cursor-pointer text-base hover:underline"
href={newSimulationUrl({
...displayMode,
mobileLaw: true,
parametersVariableName: decomposition.name,
})}
data-sveltekit-noscroll
>{decomposition.short_label ?? decomposition.label}</a
>
{/if}
</div>
{:else}
{#each [...iterToDepth(depth)] as _level}
<div class="ml-2 h-full border-l border-le-gris-dispositif">
&nbsp;
</div>
{/each}
{#if visibleChildren === undefined}
<!-- Leaf node (except the first one, that belongs to trunk) -->
<div class="ml-4">
{#if decomposition.obsolete || decomposition.last_value_still_valid_on === undefined || decomposition.last_value_still_valid_on < (new Date().getFullYear() - 2).toString()}
<Tooltip
allowFlip={false}
arrowClass="bg-gray-100"
widthClass="w-80"
initialPlacement="bottom"
>
<iconify-icon
class="mr-1 shadow-none {decomposition.obsolete
? 'text-[#FF4133]'
: 'text-[#FFAC33]'}"
icon="material-symbols:warning-rounded"
width="16"
height="16"
></iconify-icon>
{#snippet tooltip()}
<div
class="overflow-hidden rounded-lg border border-gray-200 bg-white shadow-2xl"
>
<div
class="border-b border-gray-200 bg-gray-100 px-3 py-2"
>
<h3 class="font-semibold text-gray-900">
⚠️ Ce dispositif n'est peut-être pas à jour
</h3>
</div>
<div class="px-3 py-2 text-sm font-light text-gray-500">
Dernière relecture :
{#if decomposition.last_value_still_valid_on === undefined}
date indéterminée
{:else}{dateFormatter(
new Date(decomposition.last_value_still_valid_on),
)}
{/if}
{#if decomposition.obsolete}
; Obsolète !{/if}
</div>
</div>
{/snippet}
</Tooltip>
{/if}
</div>
{#if displayMode.edit !== undefined}
<!-- Leaf decomposition node in variable inputs mode => link -->
<a
class="cursor-pointer overflow-x-hidden text-ellipsis font-serif text-base hover:z-20 hover:overflow-x-visible hover:bg-white hover:text-le-gris-dispositif hover:underline"
href={newSimulationUrl({
...displayMode,
variableName: decomposition.name,
})}
data-sveltekit-noscroll
>{decomposition.short_label ?? decomposition.label}</a
>
{:else}
<!-- Leaf decomposition node with parameters in parameters mode => link -->
<a
class="cursor-pointer overflow-x-hidden text-ellipsis font-serif text-base hover:z-20 hover:overflow-x-visible hover:bg-white hover:text-le-gris-dispositif hover:underline"
href={newSimulationUrl({
...displayMode,
mobileLaw: true,
parametersVariableName: decomposition.name,
})}
data-sveltekit-noscroll
>{decomposition.short_label ?? decomposition.label}</a
>
{/if}
{:else}
<!-- Non-trunk, non-leaf variablev-->
{#if decomposition.open}
<button class="p-0 text-black" onclick={() => zoomOut(index)}>
<iconify-icon
class="align-[-0.2rem] text-lg"
icon="ri-arrow-up-s-line"
></iconify-icon>
</button>
{:else}
<button class="p-0 text-black" onclick={() => zoomIn(index)}>
<iconify-icon
class="align-[-0.2rem] text-lg"
icon="ri-arrow-right-s-line"
></iconify-icon>
</button>
{/if}
{#if displayMode.edit !== undefined}
<!-- Non-lead decomposition node in variable inputs mode => no-link -->
<button
class="cursor-pointer overflow-x-hidden text-ellipsis font-serif text-base text-black hover:z-20 hover:overflow-x-visible hover:bg-white hover:text-black hover:underline"
onclick={() => {
if (decomposition.open) {
zoomOut(index)
} else {
zoomIn(index)
}
}}
>
{decomposition.short_label ?? decomposition.label}
</button>
{:else}
<!-- Leaf decomposition node with parameters in parameters mode => link -->
<a
class="cursor-pointer overflow-x-hidden text-ellipsis font-serif text-base hover:z-20 hover:overflow-x-visible hover:bg-white hover:text-le-gris-dispositif hover:underline"
href={newSimulationUrl({
...displayMode,
parametersVariableName: decomposition.name,
})}
onclick={preventDefault(() => {
if (decomposition.open) {
zoomOut(index)
} else {
zoomIn(index)
}
goto(
newSimulationUrl({
...displayMode,
parametersVariableName: decomposition.name,
}),
{ noScroll: true },
)
})}
data-sveltekit-noscroll
>{decomposition.short_label ?? decomposition.label}</a
>
{/if}
{/if}
{/if}
</div>
{#each rows as { calculationName, deltaAtVectorIndexArray }}
<!-- Decomposition compared amounts -->
{#if !decomposition.open || trunk || index === 0}
<div class="relative flex items-center whitespace-nowrap">
{#if !decomposition.open && !trunk}
<div class="absolute">
{#each iterToDepth(depth)}
<div class="ml-2 h-full border-l border-le-gris-dispositif">
&nbsp;
</div>
{/each}
</div>
{/if}
<div
class="justify-center {decomposition.open &&
trunk &&
visibleChildren.length > 1 &&
calculationName === firstCalculationName
? ''
: ' border-none'} {calculationName === firstCalculationName
? ''
: '-mt-1 mb-1'} flex w-full text-sm"
>
{#if decomposition.open || index === 0}
<!---Composant loader pour les valeurs intermédiaires-->
{#if showLoader && runningCalculationNames.length > 0}
{#if runningCalculationNames.includes("law") || runningCalculationNames.includes("revaluation")}<span
class="mx-1 animate-pulse-2 bg-gray-500 px-1 text-black blur-xs"
>
<span class="text-white blur">value €</span>
</span>
{/if}
{#if runningCalculationNames.includes("bill")}
<span
class="mx-1 animate-pulse-2 bg-le-rouge-bill px-1 text-black blur-xs"
>
<span class="text-white blur">value €</span>
</span>
{/if}
{#if runningCalculationNames.includes("amendment") && modificationsAmendmentCount > 0}
<span
class="mx-1 animate-pulse-2 bg-le-jaune px-1 text-black blur-xs"
>
<span class="text-white blur">value €</span>
</span>
{/if}
<!--Valeurs du waterfall des montants intermédiaires -->
{:else if trunk || index === 0}
{#if deltaAtVectorIndexArray[0] === deltaAtVectorIndexArray[1]}
{#if decomposition.open && trunk}
<span class="mx-2 text-gray-500">=</span>
{/if}
<span
class="text-sm {calculationName === firstCalculationName
? rows.find((row) => row.calculationName === 'bill') ===
undefined
? rows.find(
(row) => row.calculationName === 'amendment',
) === undefined
? 'text-gray-500'
: 'text-gray-500 line-through-amendment'
: 'text-gray-500 line-through-bill'
: calculationName === 'bill'
? rows.find(
(row) => row.calculationName === 'amendment',
) === undefined
? 'text-le-rouge-bill'
: 'text-le-rouge-bill line-through-amendment'
: 'bg-le-jaune'}"
>{deltaFormatter(deltaAtVectorIndexArray[0] ?? 0)}</span
>
{:else}
<div class="flex w-full justify-center">
<div class="mx-4 w-1/2">
{#if decomposition.open && trunk}
<span class="mx-2 text-gray-500">=</span>
{/if}
<span
class="text-right text-sm {calculationName ===
firstCalculationName
? rows.find(
(row) => row.calculationName === 'bill',
) === undefined
? rows.find(
(row) => row.calculationName === 'amendment',
) === undefined
? 'text-gray-500'
: 'text-gray-500 line-through-amendment'
: 'text-gray-500 line-through-bill'
: calculationName === 'bill'
? rows.find(
(row) => row.calculationName === 'amendment',
) === undefined
? 'text-le-rouge-bill'
: 'text-le-rouge-bill line-through-amendment'
: 'bg-le-jaune'}"
>{deltaFormatter(
deltaAtVectorIndexArray[0] ?? 0,
)}</span
>
</div>
<div class="mx-4 w-1/2">
{#if decomposition.open && trunk}
<span class="mx-2 text-gray-500">=</span>
{/if}
<span
class="text-left text-sm {calculationName ===
firstCalculationName
? rows.find(
(row) => row.calculationName === 'bill',
) === undefined
? rows.find(
(row) => row.calculationName === 'amendment',
) === undefined
? 'text-gray-500'
: 'text-gray-500 line-through-amendment'
: 'text-gray-500 line-through-bill'
: calculationName === 'bill'
? rows.find(
(row) => row.calculationName === 'amendment',
) === undefined
? 'text-le-rouge-bill'
: 'text-le-rouge-bill line-through-amendment'
: 'bg-le-jaune'}"
>{deltaFormatter(
deltaAtVectorIndexArray[1] ?? 0,
)}</span
>
</div>
</div>
{/if}
{/if}
<!--Montant des dispositifs-->
{:else if deltaAtVectorIndexArray[0] === deltaAtVectorIndexArray[1]}
<!---Composant loader pour la valeur suivante-->
{#if showLoader && runningCalculationNames.length > 0}
{#if runningCalculationNames.includes("law") || runningCalculationNames.includes("revaluation")}<span
class="mx-1 animate-pulse-2 bg-gray-500 px-1 text-black blur-xs"
>
<span class="text-white blur">value €</span>
</span>
{/if}
{#if runningCalculationNames.includes("bill")}
<span
class="mx-1 animate-pulse-2 bg-le-rouge-bill px-1 text-black blur-xs"
>
<span class="text-white blur">value €</span>
</span>
{/if}
{#if runningCalculationNames.includes("amendment") && modificationsAmendmentCount > 0}
<span
class="mx-1 animate-pulse-2 bg-le-jaune px-1 text-black blur-xs"
>
<span class="text-white blur">value €</span>
</span>
{/if}
<!--Valeur-->
{:else}
<span
class="text-base font-bold {calculationName ===
firstCalculationName
? rows.find((row) => row.calculationName === 'bill') ===
undefined
? rows.find(
(row) => row.calculationName === 'amendment',
) === undefined
? ''
: 'line-through-amendment'
: 'line-through-bill'
: calculationName === 'bill'
? rows.find(
(row) => row.calculationName === 'amendment',
) === undefined
? 'text-le-rouge-bill'
: 'text-le-rouge-bill line-through-amendment'
: 'bg-le-jaune'}"
>{deltaFormatter(deltaAtVectorIndexArray[0] ?? 0)}</span
>
{/if}
{:else}
<!---Composant loader pour la valeur suivante-->
{#if showLoader && runningCalculationNames.length > 0}
{#if runningCalculationNames.includes("law") || runningCalculationNames.includes("revaluation")}<span
class="mx-1 animate-pulse-2 bg-gray-500 px-1 text-black blur-xs"
>
<span class="text-white blur">value €</span>
</span>
{/if}
{#if runningCalculationNames.includes("bill")}
<span
class="mx-1 animate-pulse-2 bg-le-rouge-bill px-1 text-black blur-xs"
>
<span class="text-white blur">value €</span>
</span>
{/if}
{#if runningCalculationNames.includes("amendment") && modificationsAmendmentCount > 0}
<span
class="mx-1 animate-pulse-2 bg-le-jaune px-1 text-black blur-xs"
>
<span class="text-white blur">value €</span>
</span>
{/if}
<!--Valeur dispositifs-->
{:else}
<div class="flex w-full justify-center">
<div class="mx-4 w-1/2">
<span
class="text-base font-bold {calculationName ===
firstCalculationName
? rows.find(
(row) => row.calculationName === 'bill',
) === undefined
? rows.find(
(row) => row.calculationName === 'amendment',
) === undefined
? ''
: 'line-through-amendment'
: 'line-through-bill'
: calculationName === 'bill'
? rows.find(
(row) => row.calculationName === 'amendment',
) === undefined
? 'text-le-rouge-bill'
: 'text-le-rouge-bill line-through-amendment'
: 'bg-le-jaune'}"
>{deltaFormatter(deltaAtVectorIndexArray[0] ?? 0)}</span
>
</div>
<div class="mx-4 w-1/2">
<span
class="text-base font-bold {calculationName ===
firstCalculationName
? rows.find(
(row) => row.calculationName === 'bill',
) === undefined
? rows.find(
(row) => row.calculationName === 'amendment',
) === undefined
? ''
: 'line-through-amendment'
: 'line-through-bill'
: calculationName === 'bill'
? rows.find(
(row) => row.calculationName === 'amendment',
) === undefined
? 'text-le-rouge-bill'
: 'text-le-rouge-bill line-through-amendment'
: 'bg-le-jaune'}"
>{deltaFormatter(deltaAtVectorIndexArray[1] ?? 0)}</span
>
</div>
</div>
{/if}
{/if}
</div>
</div>
{/if}
{/each}
{/each}
</div>
{/if}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment