Dreamine.UI.Maui 1.0.1
Windows(WinUI)의 네이티브 `CheckBox`는 `WidthRequest`로 줄일 수 없는 거대한 최소 너비를 가져서 라벨과의 간격이 벌어지는 문제가 있어, 처음부터 직접 그려서 만들었습니다.
로딩중...
검색중...
일치하는것 없음
DreamineLightBulb.cs
이 파일의 문서화 페이지로 가기
1namespace Dreamine.UI.Maui;
2
11public sealed class DreamineLightBulb : GraphicsView, IDrawable
12{
21 public static readonly BindableProperty IsOnProperty = BindableProperty.Create(
22 nameof(IsOn), typeof(bool), typeof(DreamineLightBulb), false, propertyChanged: OnVisualChanged);
23
32 public static readonly BindableProperty DiameterProperty = BindableProperty.Create(
33 nameof(Diameter), typeof(double), typeof(DreamineLightBulb), 96d, propertyChanged: OnDiameterChanged);
34
43 public bool IsOn
44 {
45 get => (bool)GetValue(IsOnProperty);
46 set => SetValue(IsOnProperty, value);
47 }
48
57 public double Diameter
58 {
59 get => (double)GetValue(DiameterProperty);
60 set => SetValue(DiameterProperty, value);
61 }
62
72 {
73 Drawable = this;
74 InputTransparent = true;
75 ApplySize();
76 }
77
102 public void Draw(ICanvas canvas, RectF dirtyRect)
103 {
104 var d = (float)Math.Max(32, Diameter);
105 var cx = dirtyRect.Center.X;
106 var top = dirtyRect.Top + 2f;
107 var glassFill = IsOn ? Color.FromArgb("#FFD666") : Color.FromRgba(100, 116, 139, 42);
108 var glassStroke = IsOn ? Color.FromArgb("#FFC400") : Color.FromArgb("#66758B");
109 var filament = IsOn ? Color.FromArgb("#7A4B00") : Color.FromArgb("#64748B");
110 var baseFill = Color.FromArgb("#708098");
111
112 canvas.SaveState();
113 canvas.Antialias = true;
114
115 if (IsOn)
116 {
117 canvas.FillColor = Color.FromRgba(255, 214, 102, 72);
118 canvas.FillEllipse(cx - d * .62f, top + d * .50f - d * .62f, d * 1.24f, d * 1.24f);
119 }
120
121 var glass = CreateGlassPath(cx, top, d);
122 canvas.FillColor = glassFill;
123 canvas.StrokeColor = glassStroke;
124 canvas.StrokeSize = 4;
125 canvas.FillPath(glass);
126 canvas.DrawPath(glass);
127
128 var filamentPath = new PathF();
129 filamentPath.MoveTo(cx - d * .22f, top + d * .56f);
130 filamentPath.CurveTo(cx - d * .12f, top + d * .38f, cx - d * .02f, top + d * .72f, cx + d * .10f, top + d * .53f);
131 filamentPath.CurveTo(cx + d * .16f, top + d * .44f, cx + d * .21f, top + d * .49f, cx + d * .25f, top + d * .55f);
132 canvas.StrokeColor = filament;
133 canvas.StrokeSize = 4;
134 canvas.StrokeLineCap = LineCap.Round;
135 canvas.DrawPath(filamentPath);
136
137 var neckTop = top + d * .92f;
138 var neck = new PathF();
139 neck.MoveTo(cx - d * .30f, neckTop);
140 neck.LineTo(cx + d * .30f, neckTop);
141 neck.LineTo(cx + d * .20f, neckTop + d * .26f);
142 neck.LineTo(cx - d * .20f, neckTop + d * .26f);
143 neck.Close();
144
145 canvas.FillColor = baseFill;
146 canvas.FillPath(neck);
147 FillRib(canvas, cx, neckTop + d * .10f, d * .44f);
148 FillRib(canvas, cx, neckTop + d * .22f, d * .36f);
149 FillRib(canvas, cx, neckTop + d * .34f, d * .27f);
150
151 canvas.RestoreState();
152 }
153
194 private static PathF CreateGlassPath(float cx, float top, float d)
195 {
196 var path = new PathF();
197 path.MoveTo(cx, top + d * .02f);
198 path.CurveTo(cx - d * .36f, top + d * .02f, cx - d * .52f, top + d * .27f, cx - d * .52f, top + d * .54f);
199 path.CurveTo(cx - d * .52f, top + d * .74f, cx - d * .35f, top + d * .87f, cx - d * .25f, top + d * .96f);
200 path.LineTo(cx + d * .25f, top + d * .96f);
201 path.CurveTo(cx + d * .35f, top + d * .87f, cx + d * .52f, top + d * .74f, cx + d * .52f, top + d * .54f);
202 path.CurveTo(cx + d * .52f, top + d * .27f, cx + d * .36f, top + d * .02f, cx, top + d * .02f);
203 path.Close();
204 return path;
205 }
206
247 private static void FillRib(ICanvas canvas, float cx, float y, float width)
248 {
249 canvas.FillRoundedRectangle(cx - width / 2f, y, width, 7f, 3.5f);
250 }
251
284 private static void OnVisualChanged(BindableObject bindable, object oldValue, object newValue)
285 {
286 if (bindable is DreamineLightBulb bulb)
287 bulb.Invalidate();
288 }
289
322 private static void OnDiameterChanged(BindableObject bindable, object oldValue, object newValue)
323 {
324 if (bindable is DreamineLightBulb bulb)
325 {
326 bulb.ApplySize();
327 bulb.Invalidate();
328 }
329 }
330
339 private void ApplySize()
340 {
341 var d = Math.Max(32, Diameter);
342 WidthRequest = d * 1.25;
343 HeightRequest = d * 1.65;
344 }
345}
static readonly BindableProperty IsOnProperty
static void FillRib(ICanvas canvas, float cx, float y, float width)
void Draw(ICanvas canvas, RectF dirtyRect)
static void OnDiameterChanged(BindableObject bindable, object oldValue, object newValue)
static void OnVisualChanged(BindableObject bindable, object oldValue, object newValue)
static readonly BindableProperty DiameterProperty
static PathF CreateGlassPath(float cx, float top, float d)