ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • Parameter, Ref, EventCallback
    웹 서버/Blazor 입문 2022. 4. 27. 22:34

    1. 컴포넌트화

    아래의 코드를 분석할 필요는 없다.

    User.razor

    @page "/user"
    
    @using BlazorApp.Data
    
    <h3>Online User</h3>
    
    <p>
        Users: <b>@_users.Count()</b>
    </p>
    
    <br />
    
    <ul class="list-group">
        @foreach (UserData user in _users)
        {
            <li @key="user" class="list-group-item">
                <button type="button" class="btn btn-link" @onclick="(()=>KickUser(user))">ban</button>
                <label>@user.Name</label>
            </li>
        }
    </ul>
    
    <br />
    
    <div class="container">
        <div class="row">
            <div class="col">
                <input class="form-control" placeholder="Add User" @bind-value="_inputName" />
            </div>
    
            <div class="col">
                <button class="@_btnClass" type="button" @onclick="AddUser" disabled="@(_users.Count() >= 5)">Add a User</button>
            </div>
        </div>
    </div>
    
    @code {
    
        List<UserData> _users = new List<UserData>();
    
        string _inputName;
        string _btnClass = "btn btn-primary";
    
        protected override void OnInitialized() // User에 접근해서 페이지를 열면 초기화되는 함수
        {
            _users.Add(new UserData() { Name = "Rookiss" });
            _users.Add(new UserData() { Name = "Faker" });
            _users.Add(new UserData() { Name = "Deft" });
            RefreshButton();
        }
    
        void AddUser()
        {
            _users.Add(new UserData() { Name = _inputName });
            _inputName = "";
            RefreshButton();
        }
    
        void KickUser(UserData user)
        {
            _users.Remove(user);
            RefreshButton();
        }
    
        void RefreshButton() // 유저수가 홀수짝수에 따라 버튼색이 바뀜
        {
            if (_users.Count % 2 == 0)
                _btnClass = "btn btn-primary";
            else
                _btnClass = "btn btn-secondary";
        }
    }

    우선 위의 코드 중에서 다음의 코드를 가져와 컴포넌트로 만들 수 있다.

     

    ShowUser.razor

    <p>
        Users: <b>@_users.Count()</b>
    </p>
    
    <br />
    
    <ul class="list-group">
        @foreach (UserData user in _users)
        {
            <li @key="user" class="list-group-item">
                <button type="button" class="btn btn-link" @onclick="(()=>KickUser(user))">ban</button>
                <label>@user.Name</label>
            </li>
        }
    </ul>

    User.razor에 있는 코드를 일부 잘라와서 ShowUser.razor파일에 넣었다.

    참고로 컴포넌트 목적의 razor파일은 @page와 같은 경로 설정의 필요성이 사라진다.

     

    User.razor

    @page "/user"
    
    @using BlazorApp.Data
    
    <h3>Online User</h3>
    
    <ShowUser></ShowUser>
    
    <br />

    그리고 원래의 코드가 있던자리에는 위와같이 <ShowUser></ShowUser>를 채워넣어주면된다. ShowUser는 User파일에서 컴포넌트로써 작동하고 있다.

    2. Parameter

    컴포넌트화 했을 때는 한 가지 문제점이 있다. User.razor에서 정의된 데이터를 ShowUser.razor가 사용할 수 없다는 문제이다. 그래서 이러한 것을 해결하기 위해 Parameter라는 기능을 활용할 수 있다.

     

    ShowUser.razor

    @code {
        [Parameter]
        public List<UserData> Users { get; set; } // 파라미터를 사용하기 위해선 프로퍼티를 써야함.
    }

    [Parameter]는 파라미터를 사용하겠다는 뜻이다.

    그리고 넘겨받을 List타입을 정의하고, public과 프로퍼티를 사용해야한다.

     

    User.razor

    <ShowUser Users="_users"></ShowUser>
    
    @code {
        List<UserData> _users = new List<UserData>();
    }

    그리고 User.razor에서는 위와같은 방법으로 ShowUser.razor에 리스트 정보를 넘겨줄 수 있다.

     

    3. Ref

    파라미터로 자료를 넘겨줄 수 있다는 것 까진 알았다. 그런데 한 가지 문제점이 더 있다.

    User.razor에 정의된 함수를 ShowUser.razor에서 어떻게 처리하냐는 문제이다.

    이러한 문제는 ref키워드를 통해서 User.razor에서 ShowUser.razor에 있는 함수에 접근하는 방식으로 처리한다.

     

    ShowRazor.razor

    @code {
        [Parameter]
        public List<UserData> Users { get; set; } // 파라미터를 사용하기 위해선 프로퍼티를 써야함.
    
        public void AddUser(UserData user)
        {
            Users.Add(user);
        }
    }

    우선은 ShowUser.razor에 @code부분에서 public형으로 함수를 정의해준다.

     

    User.razor

    <ShowUser Users="_users" @ref="_showUser"></ShowUser>
    
    @code {
        List<UserData> _users = new List<UserData>();
        ShowUser _showUser; // ShowUser형 정의
        string _inputName;
    
        void AddUser()
        {
            _showUser.AddUser(new UserData() { Name = _inputName }); // ShowUser의 함수 사용
            _inputName = "";
        }

    그리고 ShowUser타입의 변수를 정의하고 정의된 변수 ref키워드로 정의된 변수(_showUser)와 바인딩을 하면 ShowUser에 대한 함수 접근이 가능해진다.

     

    4. EventCallback

    ref를 통해서 부모 컴포넌트에서 자식 컴포넌트의 함수와 변수를 사용할 수 있었다. 반대로 자식 컴포넌트(ShowUser.razor)에서 부모 컴포넌트(User.razor)의 함수를 호출하고 싶을 때는 어떻게 해야할까?

     

    ShowUser.razor

    @code {
        [Parameter]
        public List<UserData> Users { get; set; } // 파라미터를 사용하기 위해선 프로퍼티를 써야함.
    
        [Parameter]
        public EventCallback CallbackTest { get; set; } //Action과 Fucn도 사용이 가능하지만 EventCallback을 추천
    
        protected override void OnInitialized() // User에 접근해서 페이지를 열면 초기화되는 함수
        {
            Users.Add(new UserData() { Name = "Rookiss" });
            Users.Add(new UserData() { Name = "Faker" });
            Users.Add(new UserData() { Name = "Deft" });
        }
    
        public void AddUser(UserData user)
        {
            Users.Add(user);
        }
    
        public void KickUser(UserData user)
        {
            Users.Remove(user);
    
            CallbackTest.InvokeAsync(null); // EventCallback 사용방식
        }
    }

    파라미터로 이벤트함수 관련인 EventCallback으로 변수를 선언한다.

    그리고  KickUser가 호출되면 EventCallback이 간접 호출이 되게 KickUser()함수안에 구현하였다.

     

    User.razor

    <ShowUser Users="_users" CallbackTest="CallbackTestFunc" @ref="_showUser"></ShowUser>
    
    @code {
    
        List<UserData> _users = new List<UserData>();
        ShowUser _showUser;
    
        string _inputName;
    
        void AddUser()
        {
            _showUser.AddUser(new UserData() { Name = _inputName });
            _inputName = "";
        }
    
        void KickUser(UserData user)
        {
            _showUser.KickUser(user);
        }
    
        void CallbackTestFunc()
        {
            _inputName = "CallbackTest";
            StateHasChanged();
        }
    }

    CallbackTest파라미터를 CallbackTestFunc와 바인딩을해주면 ShowUser.razor에 있는 KickUser가 호출될 때 마다

    User.razor에 있는 CallbackTestFucn()가 간접적으로 호출이된다.

    '웹 서버 > Blazor 입문' 카테고리의 다른 글

    Templated Component  (0) 2022.05.20
    Cascading Parameter  (0) 2022.05.19
    Binding  (0) 2022.04.25
Designed by Tistory.