<script>

function getProperty(obj, name) { return obj[name]; }

</script>


@inject IJSRuntime js

@code

{

ElementReference det;

bool isOpen = true;

}

<details open=@isOpen @ref=det @ontoggle='async ()=> isOpen = await js.InvokeAsync<bool>("getProperty", det, "open")'>

<summary>@(isOpen?"닫기":"열기")</summary>

@if(isOpen)

{

<span>뀨뀨</span>

}

</details>





details태그의 경우 클릭을 통해 open 속성에 따라 InnerHTML이 보여지고 숨겨지고 하는데,

Blazor입장에선 어쨋든 InnerHTML까지 다 랜더링 하고서 브라우저가 맡아서 표시하기때문에

컨텐츠가 많거나 계산이 많이필요할경우 미리 open 여부를 알아낸다면 연산을 줄일수 있게된다.


dotnet - js 간 호출이 의외로 간결하지가 못해서

더 깔끔한 방법 찾으려 별에별 삽질 하다가 이정도로 수렴.


20231016 개선판

js없이 blazor컴포넌트 기능 활용하여 개선

 


<details @attributes=attr @ontoggle='() => open = !open'>@ChildContent?.Invoke(open)</details>

@code {

[Parameter(CaptureUnmatchedValues = true)] public IDictionary<string, object>? attr { get; set; }

[Parameter] public RenderFragment<bool>? ChildContent { get; set; }

bool open = false; //details는 초기속성이 open이더라도 toggle이 발생하여 무조건 false부터 시작하면됨.

}

<Details Context="isOpen" class="my" open>

<summary>더보기</summary>

@if (isOpen)

{

<span>더봤기</span>

}

</Details>