From 1a1c8e71fcd14858f595029f089b2d4a00202b32 Mon Sep 17 00:00:00 2001
From: ogi <Administrator@S-OGI-PC>
Date: Fri, 05 Dec 2025 09:24:16 +0900
Subject: [PATCH] プロジェクトファイルを追加。

---
 HotelPms.Client.Blazor/Dialog/ColSetting.razor |  599 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 599 insertions(+), 0 deletions(-)

diff --git a/HotelPms.Client.Blazor/Dialog/ColSetting.razor b/HotelPms.Client.Blazor/Dialog/ColSetting.razor
new file mode 100644
index 0000000..e749425
--- /dev/null
+++ b/HotelPms.Client.Blazor/Dialog/ColSetting.razor
@@ -0,0 +1,599 @@
+@inject GrpcChannel Channel
+@inject IJSRuntime JSRuntime
+@inject IDialogService DialogService
+@using HotelPms.Client.Blazor.Util
+@using HotelPms.Client.Blazor.ViewModel
+@using HotelPms.Data.Common
+@using static HotelPms.Client.Blazor.Util.SystemEnum
+@if(Data != null)
+{
+<MudDialog Style="width: 800px;">
+    <DialogContent>
+        <MudGrid Justify="Justify.Center">            
+            <MudItem xs="6">
+                <MudTextField Margin="Margin.Normal" @bind-Value="Data.ReportName" Label="帳票名" Variant="Variant.Outlined"  ReadOnly="true"></MudTextField>                
+            </MudItem>
+            <MudItem xs="@(mode == 0 ? 6 : 5)">
+                <MudTextField @ref="txtOutputName" T="string" Error="@txtOutputNameError" ErrorText="@txtOutputNameErrorText" Margin="Margin.Normal" @bind-Value="Data.OutputName" Label="出力パターン" Variant="Variant.Outlined" OnBlur="OutputNameLeave"></MudTextField>                
+            </MudItem>
+            @if (mode == 1)
+            {
+                <MudItem xs="1" Style="margin: auto">
+                    <MudTooltip Text="削除" Placement="Placement.Top">
+                        <MudFab Icon="@Icons.Material.Filled.Close" Color="MudBlazor.Color.Error" Size="@Size.Medium" IconSize="@Size.Medium" OnClick="@(()=>RemoveOutput())" />
+                    </MudTooltip>
+                </MudItem>
+            }
+            <MudItem xs="6">                
+                <MudGrid>                  
+                    <MudItem xs="12">                        
+                        <label  style="
+                                box-shadow: 0 2px 7px @(mode == 0 ? "#4caf50" : "#304FFE");
+                                display: inline-flex;
+                                width: 150px;
+                                justify-content: center;
+                                border-radius: 2em;
+                                color: white;
+                                border:2px solid;
+                                align-items: center;
+                                padding:8px;
+                                letter-spacing: 2px;
+                                font-size:medium;
+                                background-color: @(mode == 0 ? "#4caf50" : "#304FFE");">
+                            <MudIcon Icon="@Icons.Material.Filled.GridView" Size="@Size.Small"/>@(mode == 0 ? "新規モード" : "変更モード")
+                        </label>
+                        <!-- <MudChip Size="Size.Large" Icon="@Icons.Material.Filled.GridView" Color="MudBlazor.Color.Secondary" Style="width: 150px;">新規</MudChip>  -->                  
+                    </MudItem>
+                    <MudItem xs="9">                        
+                        <MudTextField Margin="Margin.Dense" @bind-Value="Data.Sort1" Label="第一ソート" Variant="Variant.Outlined" ReadOnly="true" Adornment=" Adornment.End" AdornmentIcon="@Icons.Filled.Search" AdornmentColor="MudBlazor.Color.Secondary" OnAdornmentClick="@(()=>SetSort(1))"></MudTextField>
+                    </MudItem>
+                    <MudItem xs="3">
+                        <MudTooltip Text="解除" Placement="Placement.Top">
+                            <MudFab Icon="@Icons.Material.Filled.DomainDisabled" Color="MudBlazor.Color.Primary" Size="@Size.Small" IconSize="@Size.Small" OnClick="@(()=>ClearSort(1))" />
+                        </MudTooltip>
+                    </MudItem>
+                    <MudItem xs="9">
+                        <MudTextField Margin="Margin.Dense" @bind-Value="Data.Sort2" Label="第二ソート" Variant="Variant.Outlined" ReadOnly="true" Adornment=" Adornment.End" AdornmentIcon="@Icons.Filled.Search" AdornmentColor="MudBlazor.Color.Secondary" OnAdornmentClick="@(()=>SetSort(2))"></MudTextField>
+                    </MudItem>
+                    <MudItem xs="3">
+                        <MudTooltip Text="解除" Placement="Placement.Top">
+                            <MudFab Icon="@Icons.Material.Filled.DomainDisabled" Color="MudBlazor.Color.Primary" Size="@Size.Small" IconSize="@Size.Small" OnClick="@(()=>ClearSort(2))" />
+                        </MudTooltip>
+                    </MudItem>
+                </MudGrid> 
+            </MudItem>
+            <MudItem xs="6">
+                <MudPaper Width="100%" Height="200px;" Style="overflow:auto;">
+                    <MudList Clickable="true" Dense="true" @bind-SelectedItem="SelectedOutput">
+                        @foreach(HotelPms.Data.Master.Output item in Data.OutputList)
+                        {
+                            <MudListItem Text="@item.Name" Value="@item.Name" Tag = "@item"/>
+                        }
+                    </MudList>
+                </MudPaper>                
+            </MudItem>
+            <MudItem xs="4">
+                <MudText Typo="Typo.h5" GutterBottom="true">項目一覧</MudText>
+                <MudPaper Width="100%" Height="220px;" Style="overflow:auto;">
+                    <MudList Clickable="true" Dense="true" @bind-SelectedItem="SelectedCol">
+                        @foreach(string item in  Data.OrgColList)
+                        {
+                            <MudListItem Text="@item" Value="@item"/>
+                        }
+                    </MudList>
+                </MudPaper> 
+            </MudItem>
+            <MudItem xs="2">
+                <MudButton Variant="Variant.Filled" EndIcon="@Icons.Material.Filled.ArrowForward" Color="MudBlazor.Color.Primary" Class="mt-10" Style="width: 110px;" OnClick="AddCol">追加</MudButton>
+                <MudButton Variant="Variant.Filled" EndIcon="@Icons.Material.Filled.ArrowForwardIos" Color="MudBlazor.Color.Primary" Class="mt-2" Style="width: 110px;" OnClick="AddAllCol">一括</MudButton>
+                <MudButton Variant="Variant.Filled" EndIcon="@Icons.Material.Filled.Remove" Color="MudBlazor.Color.Primary" Class="mt-2" Style="width: 110px;" OnClick="DelCol">削除</MudButton>
+                <MudButton Variant="Variant.Filled" EndIcon="@Icons.Material.Filled.ArrowUpward" Color="MudBlazor.Color.Primary" Class="mt-2" Style="width: 110px;" OnClick="UpCol">一つ上</MudButton>
+                <MudButton Variant="Variant.Filled" EndIcon="@Icons.Material.Filled.ArrowDownward" Color="MudBlazor.Color.Primary" Class="mt-2" Style="width: 110px;" OnClick="DownCol">一つ下</MudButton>
+            </MudItem>
+            <MudItem xs="6">
+                <MudGrid>                  
+                    <MudItem xs="7">
+                        <MudText Typo="Typo.h5">出力項目</MudText>
+                    </MudItem>
+                    <MudItem xs="5">                        
+                        <MudButton Variant="Variant.Filled" EndIcon="@Icons.Material.Filled.Clear" Color="MudBlazor.Color.Primary" Style="width: 110px;" OnClick="ClearCol">クリア</MudButton>                        
+                    </MudItem>
+                    <MudItem xs="12">
+                        <MudTable id="@tableOwnerID" Items="@Data.Rows" Dense="true" Hover="true" ReadOnly="false" FixedHeader="true" Height="200px;" Striped ="true" T="ColSettingRow" OnRowClick="OnRowClick">
+                            <ColGroup>
+                                <col />
+                                <col style="width:50px;" />
+                                <col style="width:100px;" />
+                            </ColGroup>
+                            <HeaderContent>
+                                <MudTh>項目</MudTh>
+                                <MudTh>固定</MudTh>
+                                <MudTh>列幅</MudTh>
+                            </HeaderContent>
+                            <RowTemplate>
+                                <MudTd DataLabel="項目" Class="@context.ClassName">@context.Name</MudTd>
+                                <MudTd DataLabel="固定" Class="@context.ClassName"><MudCheckBox Checked="@context.Frozen" Dense="true" T="bool" CheckedChanged="((v)=>CheckedChanged(v, context))"></MudCheckBox></MudTd>
+                                <MudTd DataLabel="列幅" Class="@context.ClassName">
+                                        <MudNumericField @bind-Value="@context.Width" Required Min="1" TextChanged="TextChanged" />
+                                </MudTd>
+                            </RowTemplate>
+                        </MudTable>
+                    </MudItem>
+                </MudGrid>
+            </MudItem>
+        </MudGrid> 
+    </DialogContent>
+    <DialogActions>
+        <MudGrid Spacing="2" Justify="Justify.Center" Class="my-3">            
+            <MudItem>
+                <MudButton Variant="Variant.Filled" Color="MudBlazor.Color.Primary" OnClick="Save" StartIcon="@Icons.Filled.Save" Style="width: 180px; height: 40px;">保存</MudButton>
+            </MudItem>
+            <MudItem>
+                <MudButton Variant="Variant.Filled" Color="MudBlazor.Color.Primary" OnClick="Close" StartIcon="@Icons.Filled.Close" Style="width: 180px; height: 40px;">キャンセル</MudButton>
+            </MudItem>
+        </MudGrid>                
+    </DialogActions>
+</MudDialog>
+}
+
+<style>
+#col-setting-grid .mud-input-control>.mud-input-control-input-container>div.mud-input.mud-input-text {
+    margin-top: 0px;
+}
+
+#col-setting-grid .mud-input>input.mud-input-root,div.mud-input-slot.mud-input-root {
+    padding: 0 0 7px;
+}
+
+#col-setting-grid .mud-table-cell .mud-checkbox {
+    margin: -2px;
+}
+
+#col-setting-grid .mud-table-cell {
+    padding: 6px 6px 6px 6px;
+    padding-inline-start: 6px;padding-inline-end: 6px;
+}
+
+#col-setting-grid .tr-select {
+    color: var(--mud-palette-primary);
+    background-color: var(--mud-palette-primary-hover);
+    <!-- background-color: rgba(223,235,242, 0.77); -->
+}
+
+</style>
+
+@code {
+    [CascadingParameter] MudDialogInstance MudDialog { get; set; }
+    [Parameter]public ColSettingData Data { get; set; }
+    private int mode = 0;  //0.新規 1.変更
+    private string selectCol = string.Empty;
+    private int selectRowID = -1;
+    private List<string> colListCopy = new List<string>();
+    private string tableOwnerID = "col-setting-grid";
+    private DataTable sortTable = new DataTable();
+    private MudTextField<string> txtOutputName;
+    private bool txtOutputNameError = false;
+    private string txtOutputNameErrorText = string.Empty;
+    private OutputAccess outputAccess;
+    private HotelPms.Data.Master.Output outputEdit = null;
+
+    private MudListItem selectedOutput;
+
+    /// <summary>
+    /// bindValue対応
+    /// </summary>
+    MudListItem SelectedOutput
+    {
+        get { return selectedOutput; }
+        set 
+        {
+            selectedOutput = value;
+            SelectedItemChanged(selectedOutput);
+        }
+    }
+
+    private MudListItem selectedCol;
+
+    /// <summary>
+    /// bindValue対応
+    /// </summary>
+    MudListItem SelectedCol
+    {
+        get { return selectedCol; }
+        set 
+        {
+            selectedCol = value;
+            SelectedColChanged(selectedCol);
+        }
+    }
+
+    /// <summary>
+    /// ※長い時間の処理をここに入れるな
+    /// </summary>
+    protected override void OnInitialized()
+    {
+        if(outputAccess == null) { outputAccess = new OutputAccess(Channel); }
+
+        if (Data.OrgColList.Count > 0 && colListCopy.Count == 0) 
+        {
+            colListCopy.AddRange(Data.OrgColList);
+            selectCol = Data.OrgColList[0]; //初期値
+
+            //ソート選択用
+            sortTable.Columns.Add("項目ID");
+            sortTable.Columns.Add("項目名");
+            int id = 1;
+            foreach(string item in colListCopy)
+            {
+                DataRow row = sortTable.NewRow();
+                sortTable.Rows.Add(row);
+                row.ItemArray = new object[] { id, item };
+                id++;
+            }
+        }  
+        base.OnInitialized();
+    }
+
+    private void SelectedItemChanged(MudListItem item)
+    {
+        EnvironmentSetting.Debug($"SelectedItemChanged⇒Begin:{DateTime.Now.ToString("HH:mm:ss fff")}");
+        Data.OutputName = item?.Text;
+
+        outputEdit = (item?.Tag as HotelPms.Data.Master.Output);
+        Data.OutputID = outputEdit.ID;
+        mode = 1;  //変更モードへ
+
+        //列の表示
+        Dictionary<string , int> dict = new Dictionary<string, int>();
+        Data.Rows.Clear();
+        int id = 0;
+        foreach(HotelPms.Data.Master.OutputItem outputItem in outputEdit.Items)
+        {
+            Data.Rows.Add(new ColSettingRow
+            {
+                ID = ++id,
+                Name = outputItem.Name,
+                Width = (int)outputItem.Width,
+                Frozen = id <= outputEdit.FixedID,
+        });
+            dict.Add(outputItem.Name, 0);
+        }
+        selectRowID = -1;
+
+        selectCol = string.Empty;
+        Data.OrgColList.Clear();
+        foreach (string col in colListCopy)
+        {
+            if (dict.ContainsKey(col)) { continue; }
+            Data.OrgColList.Add(col);
+        }
+
+        if (Data.OrgColList.Count > 0)
+        {
+            selectCol = Data.OrgColList[0]; //初期値
+        }
+
+        EnvironmentSetting.Debug($"SelectedItemChanged⇒End:{DateTime.Now.ToString("HH:mm:ss fff")}");
+    }
+
+    /// <summary>
+    /// 列選択
+    /// </summary>
+    /// <param name="item"></param>
+    private void SelectedColChanged(MudListItem item)
+    {
+        selectCol = item?.Text;
+    }
+
+    /// <summary>
+    /// 行選択
+    /// </summary>
+    /// <param name="e"></param>
+    private void OnRowClick(TableRowClickEventArgs<ColSettingRow> e)
+    {
+        foreach(ColSettingRow row in Data.Rows)
+        {
+            if (row.ID == e.Item.ID)
+            {
+                row.Select();
+                selectRowID = row.ID - 1;
+            }
+            else
+            {
+                row.ClassName = "";
+            }
+        }
+
+        //MudDialog.Close(DialogResult.Ok(e.Item));
+    }
+
+    /// <summary>
+    /// ソート設定
+    /// </summary>
+    /// <param name="index"></param>
+    private async void SetSort(int index)
+    {
+        var parameters = new DialogParameters { ["Data"]=sortTable };
+        var dialog = DialogService.Show<SelectList>($"第{(index == 1 ? "一" : "二")}ソート順設定", parameters);
+        var ret = await dialog.Result;
+        if (!ret.Cancelled)
+        {
+            var row = ret.Data as DataRow;
+            if(index == 1)
+            {
+                Data.Sort1 = row[1].ToString();
+            }
+            else
+            {
+                Data.Sort2 = row[1].ToString();
+            }
+            StateHasChanged();
+        }
+    }
+
+    /// <summary>
+    /// ソート解除
+    /// </summary>
+    /// <param name="index">1.第一ソート 2.第二ソート</param>
+    private void ClearSort(int index)
+    {
+        if (index == 1)
+        {
+            Data.Sort1 = string.Empty;
+        }
+        else
+        {
+            Data.Sort2 = string.Empty;
+        }
+    }
+
+    private void TextChanged(string value)
+    {
+        //foreach(ColSettingRow row in Data.Rows)
+        //{
+        //    row.Width = CConvert.ToInt(value);
+        //}
+    }
+
+    private void CheckedChanged(bool value, ColSettingRow curRow)
+    {
+        foreach(ColSettingRow row in Data.Rows)
+        {
+            if (row.ID < curRow.ID)
+            {
+                if (value) { row.Frozen = value; }
+            }
+            else if (row.ID == curRow.ID)
+            {
+                row.Frozen = value;
+            }
+            else
+            {
+                row.Frozen = false;
+            }
+        }
+    }
+
+    /// <summary>
+    /// パターン名のチェック
+    /// </summary>
+    /// <param name="value"></param>
+    /// <returns></returns>
+    private bool IsVaildOutputName(string value)
+    {
+        if (string.IsNullOrEmpty(value))
+        {            
+            txtOutputNameError = true;
+            txtOutputNameErrorText = "名称を入力してください。";
+            return false;
+        }
+        else
+        {
+            txtOutputNameError = false;
+            txtOutputNameErrorText = string.Empty;
+            return true;
+        }        
+    }
+
+    private void OutputNameLeave(FocusEventArgs e)
+    {
+        IsVaildOutputName(Data.OutputName);
+    }
+
+    private async Task RemoveOutput()
+    {
+        var parameters = new DialogParameters { ["MsgType"]=EMessageType.YesNo, ["Title"]="削除" ,["Data"]=  new List<string> { $"「{outputEdit.Name}」を削除しますか?" } };
+        var dialog = DialogService.Show<MessageBox>(string.Empty, parameters);
+        var result = await dialog.Result;
+        if (result.Cancelled)
+        {
+            return;
+        }
+
+        await outputAccess.RemoveAsync($" MachineName = '{outputEdit.MachineName}' AND UserName = '{outputEdit.UserName}' AND ReportID = {outputEdit.ReportID} AND ID = {outputEdit.ID}");
+        MudDialog.Close(DialogResult.Ok("2"));
+    }
+
+    /// <summary>
+    /// 登録
+    /// </summary>
+    private async void Save()
+    {
+        //チェック
+        if (!IsVaildOutputName(Data.OutputName))
+        {
+            await txtOutputName.FocusAsync();
+            return;
+        }
+
+        if(Data.Rows.Count == 0)
+        {
+            await DialogService.ShowMessageBox("出力項目一覧","出力項目を選択してください。");
+            return;
+        }
+
+        //Outputの登録
+        HotelPms.Data.Master.Output output = mode == 1 ? outputEdit : new HotelPms.Data.Master.Output
+        {
+            MachineName = "localhost",
+            UserName = "Web",
+            ReportID = Data.ReportID,
+            ID = Data.OutputID,
+            Name = Data.OutputName,
+            FixedID = 0,
+            Sort = $"{Data.Sort1},{Data.Sort2}",
+        };
+
+        if(mode == 1)
+        {
+            output.Name = Data.OutputName;
+            output.Sort = $"{Data.Sort1},{Data.Sort2}";
+            output.Items.Clear();
+        }
+
+        int maxFixedID = 0;
+        foreach(ColSettingRow row in Data.Rows)
+        {
+            if(row.Frozen && row.ID > maxFixedID) { maxFixedID = row.ID; }
+            Data.Master.OutputItem detail = new Data.Master.OutputItem
+            {
+                Name = row.Name,
+                Width = row.Width,
+            };
+            output.Items.Add(detail);
+        }
+
+        output.FixedID = maxFixedID;
+        DataResult result = mode == 0 ? await outputAccess.AddAsync(output) : await outputAccess.UpdateAsync(output);
+
+        MudDialog.Close(DialogResult.Ok("1"));
+        //if (mode == 0)
+        //{
+        //    mode = 1; //変更モードへ
+        //    Data.OutputList.Add(output);  //明細あり
+        //}
+        //StateHasChanged();
+    }
+
+    /// <summary>
+    /// 画面閉じる
+    /// </summary>
+    private void Close()
+    {
+        MudDialog.Cancel();
+    }
+
+    /// <summary>
+    /// 列追加
+    /// </summary>
+    private void AddCol()
+    {
+        if(selectCol.Length == 0) { return; }
+        int index = Data.OrgColList.IndexOf(selectCol);
+        Data.OrgColList.RemoveAt(index);
+        Data.Rows.Add(new ColSettingRow
+        {
+            ID = Data.Rows.Count + 1,
+            Name = selectCol,
+        });
+
+        //mud-selected-item
+        if (index >= Data.OrgColList.Count) 
+        { 
+            selectCol = Data.OrgColList.Count == 0 ? string.Empty : Data.OrgColList[index - 1];  
+        }
+        else
+        {
+            selectCol = Data.OrgColList[index];
+        }
+    }
+
+    /// <summary>
+    /// 列全部追加
+    /// </summary>
+    private void AddAllCol()
+    {
+        int id = Data.Rows.Count;
+        foreach(string item in Data.OrgColList)
+        {
+            id++;
+            Data.Rows.Add(new ColSettingRow
+            {
+                ID = id,
+                Name = item,
+            });
+        }
+
+        Data.OrgColList.Clear();
+        selectCol = string.Empty;
+    }
+
+    /// <summary>
+    /// 列削除
+    /// </summary>
+    private void DelCol()
+    {
+        if (selectRowID == -1) { return; }
+        Data.OrgColList.Add(Data.Rows[selectRowID].Name);
+        Data.Rows.RemoveAt(selectRowID);
+        if (selectRowID >= Data.Rows.Count)
+        {
+            selectRowID = Data.Rows.Count - 1;
+            if (selectRowID >= 0) { Data.Rows[selectRowID].Select(); }
+        }
+        else
+        {
+            Data.Rows[selectRowID].Select();
+
+            //以降のIDを更新
+            int id = selectRowID;
+            for (int i = selectRowID; i < Data.Rows.Count; i++)
+            {
+                Data.Rows[i].ID = ++id;
+            }
+        }
+    }
+
+    private async void UpCol()
+    {
+        if (selectRowID <= 0) { return; }
+        //上と⇒情報交換
+        Data.Rows[selectRowID].ID -= 1;
+        Data.Rows[selectRowID - 1].ID += 1;
+
+        ColSettingRow bkRow = Data.Rows[selectRowID - 1].DeepClone();
+        Data.Rows[selectRowID].CopyTo(Data.Rows[selectRowID - 1]);
+        bkRow.CopyTo(Data.Rows[selectRowID]);
+        selectRowID--;
+        await JSRuntime.SetTRTop(tableOwnerID, selectRowID);
+        StateHasChanged();
+    }
+
+    private async void DownCol()
+    {
+        if (selectRowID == Data.Rows.Count - 1) { return; }
+        //下と⇒情報交換
+        Data.Rows[selectRowID].ID += 1;
+        Data.Rows[selectRowID + 1].ID -= 1;
+
+        ColSettingRow bkRow = Data.Rows[selectRowID + 1].DeepClone();
+        Data.Rows[selectRowID].CopyTo(Data.Rows[selectRowID + 1]);
+        bkRow.CopyTo(Data.Rows[selectRowID]);
+        selectRowID++;
+        await JSRuntime.SetTRTop(tableOwnerID, selectRowID);
+    }
+
+
+
+    /// <summary>
+    /// 列クリア
+    /// </summary>
+    private void ClearCol()
+    {
+        Data.OrgColList.Clear();
+        Data.OrgColList.AddRange(colListCopy);
+        Data.Rows.Clear();
+        selectCol = Data.OrgColList.Count == 0 ? string.Empty : Data.OrgColList[0];
+        selectRowID = -1;
+    }
+}

--
Gitblit v1.10.0