1 // Copyright (C) 2019 Kazuhiro Fujieda <fujieda@users.osdn.me>
\r
3 // Licensed under the Apache License, Version 2.0 (the "License");
\r
4 // you may not use this file except in compliance with the License.
\r
5 // You may obtain a copy of the License at
\r
7 // http://www.apache.org/licenses/LICENSE-2.0
\r
9 // Unless required by applicable law or agreed to in writing, software
\r
10 // distributed under the License is distributed on an "AS IS" BASIS,
\r
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
\r
12 // See the License for the specific language governing permissions and
\r
13 // limitations under the License.
\r
16 using System.Collections.Generic;
\r
17 using System.Drawing;
\r
19 using System.Windows.Forms;
\r
20 using KancolleSniffer.Model;
\r
22 namespace KancolleSniffer.View.MainWindow
\r
24 public class QuestPanel : PanelWithToolTip
\r
26 private const int TopMargin = 5;
\r
27 private const int LeftMargin = 2;
\r
28 private const int LabelHeight = 12;
\r
29 private const int LineHeight = 14;
\r
30 private QuestLabels[] _labels;
\r
31 private QuestStatus[] _questList = new QuestStatus[0];
\r
32 private ListScroller _listScroller;
\r
35 public int MinLines { get; set; } = 4;
\r
37 private class QuestLabels : ControlsArranger
\r
39 public Label Color { get; set; }
\r
40 public Label Name { get; set; }
\r
41 public Label Count { get; set; }
\r
42 public Label Progress { get; set; }
\r
44 public override Control[] Controls => new Control[] {Color, Count, Progress, Name};
\r
47 public void CreateLabels(int lines)
\r
49 _lines = LimitLines(lines);
\r
50 _labels = new QuestLabels[_lines];
\r
52 Height = Scaler.ScaleHeight(TopMargin * 2 + LineHeight * _lines);
\r
53 for (var i = 0; i < _lines; i++)
\r
55 var y = TopMargin + i * LineHeight;
\r
56 _labels[i] = new QuestLabels
\r
60 Location = new Point(LeftMargin, y + 1),
\r
61 Size = new Size(4, LabelHeight - 1)
\r
65 Location = new Point(LeftMargin + 4, y),
\r
66 Size = new Size(193, LabelHeight)
\r
68 Count = new GrowLeftLabel
\r
70 Location = new Point(LeftMargin + 189, y),
\r
73 Progress = new Label
\r
75 Location = new Point(LeftMargin + 186, y),
\r
76 Size = new Size(29, LabelHeight),
\r
77 TextAlign = ContentAlignment.MiddleRight
\r
80 _labels[i].Arrange(this);
\r
84 SetupListScroller();
\r
87 private int LimitLines(int lines)
\r
90 return Math.Min(Math.Max(lines, MinLines), max);
\r
93 private void SetupListScroller()
\r
95 _listScroller = new ListScroller(this, _labels[0].Controls, _labels[_lines - 1].Controls)
\r
100 _listScroller.Update += ShowQuestList;
\r
101 _listScroller.StartScroll += () => { ToolTip.Active = false; };
\r
102 _listScroller.EndScroll += () => { ToolTip.Active = true; };
\r
105 public void Update(QuestStatus[] quests)
\r
107 _listScroller.DataCount = quests.Length;
\r
108 _listScroller.Position = CalcScrollPosition(quests);
\r
109 _questList = quests.Select(q => q.Clone()).ToArray();
\r
113 private int CalcScrollPosition(QuestStatus[] newQuests)
\r
115 if (newQuests.Length <= _lines)
\r
117 var current = _listScroller.Position;
\r
118 var bottomIndex = current + _lines - 1;
\r
119 if (newQuests.Length < _questList.Length)
\r
120 return bottomIndex >= newQuests.Length ? newQuests.Length - _lines : current;
\r
121 var changedIndex = 0;
\r
122 if (newQuests.Length > _questList.Length)
\r
124 changedIndex = _questList.TakeWhile((q, i) => q.Id == newQuests[i].Id).Count();
\r
126 else if (newQuests.Length == _questList.Length)
\r
128 changedIndex = _questList.TakeWhile((q, i) => q.Count.Equals(newQuests[i].Count)).Count();
\r
129 if (changedIndex == _questList.Length) // unchanged
\r
132 if (changedIndex < current)
\r
133 return changedIndex;
\r
134 if (changedIndex > bottomIndex)
\r
135 return current + changedIndex - bottomIndex;
\r
139 private void ShowQuestList()
\r
142 for (var i = 0; i < _lines; i++)
\r
144 var labels = _labels[i];
\r
145 if (i >= _questList.Length)
\r
147 ClearQuest(labels);
\r
148 ClearCount(labels.Count);
\r
151 var quest = _questList[i + _listScroller.Position];
\r
152 SetQuest(labels, quest);
\r
153 if (quest.Count.Id == 0)
\r
155 ClearCount(labels.Count);
\r
158 SetCount(labels.Count, quest.Count);
\r
160 ResumeLayout(true);
\r
161 _listScroller.DrawMark();
\r
164 private void ClearQuest(QuestLabels labels)
\r
166 labels.Color.BackColor = DefaultBackColor;
\r
167 labels.Name.Text = labels.Progress.Text = "";
\r
168 ToolTip.SetToolTip(labels.Name, "");
\r
171 private void ClearCount(Label label)
\r
174 label.ForeColor = Color.Black;
\r
175 ToolTip.SetToolTip(label, "");
\r
178 private void SetQuest(QuestLabels labels, QuestStatus quest)
\r
180 labels.Color.BackColor = quest.Color;
\r
181 labels.Name.Text = quest.Name;
\r
182 labels.Progress.Text = $"{quest.Progress:D}%";
\r
183 ToolTip.SetToolTip(labels.Name, quest.ToToolTip());
\r
186 private void SetCount(Label label, QuestCount count)
\r
188 label.Text = " " + count;
\r
189 label.ForeColor = count.Cleared ? CUDColors.Red : Color.Black;
\r
190 ToolTip.SetToolTip(label, count.ToToolTip());
\r
193 public IEnumerable<string> QuestNameList => _labels.Select(l => l.Name.Text); // for testing
\r