Skip to content
This repository was archived by the owner on Sep 25, 2024. It is now read-only.

Commit c0bfc0c

Browse files
Dominique LouisCartBlanche
Dominique Louis
authored andcommitted
[Mac] Initial Variations Implementation
1 parent 807d5c7 commit c0bfc0c

File tree

7 files changed

+229
-63
lines changed

7 files changed

+229
-63
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,135 @@
1+
using System;
2+
using System.Reflection;
3+
using AppKit;
4+
using CoreGraphics;
5+
using Foundation;
6+
using Xamarin.PropertyEditing.ViewModels;
7+
8+
namespace Xamarin.PropertyEditing.Mac
9+
{
10+
internal class CreateVariantView
11+
: BasePopOverViewModelControl
12+
{
13+
private const int FrameWidth = 250;
14+
private const int ControlSpacing = 7;
15+
private const int RightEdgeMargin = 12;
16+
17+
public CreateVariantView (IHostResourceProvider hostResources, PropertyViewModel propertyViewModel)
18+
: base (hostResources, propertyViewModel, Properties.Resources.AddVariationTitle, "pe-resource-editor-32")
19+
{
20+
Initialize (new CreateVariantViewModel (propertyViewModel.Property));
21+
}
22+
23+
private void Initialize (CreateVariantViewModel createVariantViewModel)
24+
{
25+
Frame = new CGRect (CGPoint.Empty, new CGSize (FrameWidth, 240));
26+
27+
int editorHeight = 18;
28+
29+
var FrameWidthThird = Frame.Width / 3;
30+
31+
var introduceVariation = new UnfocusableTextField {
32+
StringValue = Properties.Resources.AddVariationHelpText,
33+
TranslatesAutoresizingMaskIntoConstraints = false,
34+
};
35+
36+
AddSubview (introduceVariation);
37+
38+
this.AddConstraints (new[] {
39+
NSLayoutConstraint.Create (introduceVariation, NSLayoutAttribute.Top, NSLayoutRelation.Equal, this, NSLayoutAttribute.Top, 1f, 37f),
40+
NSLayoutConstraint.Create (introduceVariation, NSLayoutAttribute.Left, NSLayoutRelation.Equal, this, NSLayoutAttribute.Left, 1f, 18f),
41+
NSLayoutConstraint.Create (introduceVariation, NSLayoutAttribute.Width, NSLayoutRelation.Equal, this, NSLayoutAttribute.Width, 1f, 0f),
42+
NSLayoutConstraint.Create (introduceVariation, NSLayoutAttribute.Height, NSLayoutRelation.Equal, 1f, editorHeight),
43+
});
44+
45+
var controlTop = 60;
46+
47+
var okButton = new FocusableButton {
48+
BezelStyle = NSBezelStyle.Rounded,
49+
Enabled = false,
50+
Highlighted = true,
51+
Title = Properties.Resources.AddVariation,
52+
TranslatesAutoresizingMaskIntoConstraints = false,
53+
};
54+
55+
foreach (var viewModel in createVariantViewModel.VariationCategories) {
56+
57+
var name = new UnfocusableTextField {
58+
Alignment = NSTextAlignment.Right,
59+
StringValue = viewModel.Name + ":",
60+
TranslatesAutoresizingMaskIntoConstraints = false,
61+
};
62+
63+
AddSubview (name);
64+
65+
this.AddConstraints (new[] {
66+
NSLayoutConstraint.Create (name, NSLayoutAttribute.Top, NSLayoutRelation.Equal, this, NSLayoutAttribute.Top, 1f, controlTop),
67+
NSLayoutConstraint.Create (name, NSLayoutAttribute.Right, NSLayoutRelation.Equal, this, NSLayoutAttribute.Left, 1f, FrameWidthThird),
68+
NSLayoutConstraint.Create (name, NSLayoutAttribute.Height, NSLayoutRelation.Equal, 1f, editorHeight)
69+
});
70+
71+
var popUpButton = new FocusablePopUpButton {
72+
ControlSize = NSControlSize.Small,
73+
Font = NSFont.SystemFontOfSize (NSFont.SystemFontSizeForControlSize (NSControlSize.Small)),
74+
TranslatesAutoresizingMaskIntoConstraints = false,
75+
};
76+
77+
popUpButton.Activated += (o, e) => {
78+
if (o is FocusablePopUpButton fpb) {
79+
if (fpb.SelectedItem.RepresentedObject is NSObjectFacade menuObjectFacade) {
80+
if (menuObjectFacade.Target is VariationFacade vf) {
81+
vf.ViewModel.SelectedOption = vf.Option;
82+
okButton.Enabled = createVariantViewModel.CreateVariantCommand.CanExecute (null);
83+
}
84+
}
85+
}
86+
};
87+
88+
var popUpButtonList = new NSMenu ();
89+
popUpButton.Menu = popUpButtonList;
90+
91+
AddSubview (popUpButton);
92+
93+
this.AddConstraints (new[] {
94+
NSLayoutConstraint.Create (popUpButton, NSLayoutAttribute.Top, NSLayoutRelation.Equal, this, NSLayoutAttribute.Top, 1f, controlTop),
95+
NSLayoutConstraint.Create (popUpButton, NSLayoutAttribute.Left, NSLayoutRelation.Equal, this, NSLayoutAttribute.Left, 1f, FrameWidthThird + ControlSpacing),
96+
NSLayoutConstraint.Create (popUpButton, NSLayoutAttribute.Width, NSLayoutRelation.Equal, this, NSLayoutAttribute.Width, 1f, -FrameWidthThird - ControlSpacing - RightEdgeMargin),
97+
NSLayoutConstraint.Create (popUpButton, NSLayoutAttribute.Height, NSLayoutRelation.Equal, 1f, editorHeight)
98+
});
99+
100+
foreach (var variation in viewModel.Variations) {
101+
popUpButtonList.AddItem (new NSMenuItem (variation.Name) {
102+
RepresentedObject = new NSObjectFacade (
103+
new VariationFacade {
104+
Option = variation,
105+
ViewModel = viewModel })
106+
});
107+
}
108+
109+
controlTop += editorHeight + 8;
110+
}
111+
112+
okButton.Activated += (sender, e) => {
113+
// TODO Add the Variation
114+
115+
PopOver.Close ();
116+
};
117+
118+
AddSubview (okButton);
119+
120+
this.AddConstraints (new[] {
121+
NSLayoutConstraint.Create (okButton, NSLayoutAttribute.Bottom, NSLayoutRelation.Equal, this, NSLayoutAttribute.Bottom, 1, -RightEdgeMargin),
122+
NSLayoutConstraint.Create (okButton, NSLayoutAttribute.Right, NSLayoutRelation.Equal, this, NSLayoutAttribute.Right, 1, -RightEdgeMargin),
123+
NSLayoutConstraint.Create (okButton, NSLayoutAttribute.Width, NSLayoutRelation.GreaterThanOrEqual, 1, 80)
124+
});
125+
126+
Frame = new CGRect (CGPoint.Empty, new CGSize (FrameWidth, controlTop + editorHeight * 2));
127+
}
128+
}
129+
130+
internal class VariationFacade
131+
{
132+
public PropertyVariationOption Option { get; set; }
133+
public VariationViewModel ViewModel { get; set; }
134+
}
135+
}

Xamarin.PropertyEditing.Mac/Controls/Custom/BasePopOverViewModelControl.cs

+3
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
using System;
22
using System.Collections.Generic;
33
using System.Linq;
4+
using AppKit;
45
using Xamarin.PropertyEditing.ViewModels;
56

67
namespace Xamarin.PropertyEditing.Mac
@@ -9,6 +10,8 @@ internal class BasePopOverViewModelControl : BasePopOverControl
910
{
1011
internal PropertyViewModel ViewModel { get; }
1112

13+
public AutoClosePopOver PopOver { get; internal set; }
14+
1215
public BasePopOverViewModelControl (IHostResourceProvider hostResources, PropertyViewModel viewModel, string title, string imageNamed)
1316
: base (hostResources, title, imageNamed)
1417
{

Xamarin.PropertyEditing.Mac/Controls/Custom/PropertyButton.cs

+60-30
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ internal PropertyViewModel ViewModel
1919
set {
2020
if (this.viewModel != null) {
2121
this.viewModel.PropertyChanged -= OnPropertyChanged;
22+
this.viewModel.CreateVariantRequested -= OnCreateVariantRequested;
2223
}
2324

2425
this.viewModel = value;
@@ -110,13 +111,27 @@ private void PopUpContextMenu ()
110111
this.popUpContextMenu.AddItem (NSMenuItem.SeparatorItem);
111112

112113
// TODO If we add more menu items consider making the Label/Command a dictionary that we can iterate over to populate everything.
113-
this.popUpContextMenu.AddItem (new CommandMenuItem (Properties.Resources.Reset, viewModel.ClearValueCommand) {
114+
this.popUpContextMenu.AddItem (new CommandMenuItem (Properties.Resources.Reset, this.viewModel.ClearValueCommand) {
114115
AttributedTitle = new Foundation.NSAttributedString (
115116
Properties.Resources.Reset,
116117
new CoreText.CTStringAttributes {
117118
Font = new CoreText.CTFont (PropertyEditorControl.DefaultFontName, PropertyEditorControl.DefaultFontSize + 1),
118119
})
119120
});
121+
122+
this.popUpContextMenu.AddItem (NSMenuItem.SeparatorItem);
123+
124+
if (this.viewModel.HasVariations) {
125+
this.popUpContextMenu.AddItem (new CommandMenuItem (Properties.Resources.AddVariant, this.viewModel.RequestCreateVariantCommand) {
126+
AttributedTitle = new Foundation.NSAttributedString (
127+
Properties.Resources.AddVariant,
128+
new CoreText.CTStringAttributes {
129+
Font = new CoreText.CTFont (PropertyEditorControl.DefaultFontName, PropertyEditorControl.DefaultFontSize + 1),
130+
})
131+
});
132+
133+
this.viewModel.CreateVariantRequested += OnCreateVariantRequested;
134+
}
120135
}
121136

122137
var menuOrigin = this.Superview.ConvertPointToView (new CGPoint (Frame.Location.X - 1, Frame.Location.Y + Frame.Size.Height + 4), null);
@@ -166,34 +181,34 @@ private void ToggleFocusImage (bool focused = false)
166181
private void ValueSourceChanged (ValueSource valueSource)
167182
{
168183
switch (valueSource) {
169-
case ValueSource.Binding:
170-
ToolTip = Properties.Resources.Binding;
171-
break;
172-
173-
case ValueSource.Default:
174-
ToolTip = Properties.Resources.Default;
175-
return;
176-
177-
case ValueSource.Local:
178-
ToolTip = Properties.Resources.Local;
179-
break;
180-
181-
case ValueSource.Inherited:
182-
ToolTip = Properties.Resources.Inherited;
183-
break;
184-
185-
case ValueSource.Resource:
186-
ToolTip = (this.viewModel?.Resource?.Name != null) ? String.Format (Properties.Resources.ResourceWithName, this.viewModel.Resource.Name) : Properties.Resources.Resource;
187-
break;
188-
189-
case ValueSource.Unset:
190-
ToolTip = Properties.Resources.Unset;
191-
break;
192-
193-
default:
194-
// To Handle ValueSource.DefaultStyle, ValueSource.Style etc.
195-
ToolTip = string.Empty;
196-
break;
184+
case ValueSource.Binding:
185+
ToolTip = Properties.Resources.Binding;
186+
break;
187+
188+
case ValueSource.Default:
189+
ToolTip = Properties.Resources.Default;
190+
return;
191+
192+
case ValueSource.Local:
193+
ToolTip = Properties.Resources.Local;
194+
break;
195+
196+
case ValueSource.Inherited:
197+
ToolTip = Properties.Resources.Inherited;
198+
break;
199+
200+
case ValueSource.Resource:
201+
ToolTip = (this.viewModel?.Resource?.Name != null) ? String.Format (Properties.Resources.ResourceWithName, this.viewModel.Resource.Name) : Properties.Resources.Resource;
202+
break;
203+
204+
case ValueSource.Unset:
205+
ToolTip = Properties.Resources.Unset;
206+
break;
207+
208+
default:
209+
// To Handle ValueSource.DefaultStyle, ValueSource.Style etc.
210+
ToolTip = string.Empty;
211+
break;
197212
}
198213

199214
ToggleFocusImage ();
@@ -228,13 +243,28 @@ private void OnResourceRequested (object sender, EventArgs e)
228243
Appearance = EffectiveAppearance
229244
};
230245

231-
var resourceSelectorPopOver = new AutoClosePopOver(this.hostResources) {
246+
var resourceSelectorPopOver = new AutoClosePopOver (this.hostResources) {
232247
ContentViewController = new NSViewController (null, null) { View = requestResourceView },
233248
};
234249

235250
requestResourceView.PopOver = resourceSelectorPopOver;
236251

237252
resourceSelectorPopOver.Show (requestResourceView.Frame, (NSView)this, NSRectEdge.MinYEdge);
238253
}
254+
255+
private void OnCreateVariantRequested (object sender, CreateVariantEventArgs e)
256+
{
257+
var createVariantView = new CreateVariantView (this.hostResources, this.viewModel) {
258+
Appearance = EffectiveAppearance
259+
};
260+
261+
var createVariantPopOver = new AutoClosePopOver (this.hostResources) {
262+
ContentViewController = new NSViewController (null, null) { View = createVariantView },
263+
};
264+
265+
createVariantView.PopOver = createVariantPopOver;
266+
267+
createVariantPopOver.Show (createVariantView.Frame, (NSView)this, NSRectEdge.MinYEdge);
268+
}
239269
}
240270
}

Xamarin.PropertyEditing.Mac/Controls/CustomExpressionView.cs

-2
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,6 @@ internal class CustomExpressionView : BasePopOverViewModelControl
1515
private const string PreviewCustomExpressionString = "PreviewCustomExpression";
1616
private const string AutocompleteItemsString = "AutocompleteItems";
1717

18-
public AutoClosePopOver PopOver { get; internal set; }
19-
2018
public CustomExpressionView (IHostResourceProvider hostResources, PropertyViewModel viewModel)
2119
: base (hostResources, viewModel, Properties.Resources.CustomExpression, "pe-custom-expression-32")
2220
{

Xamarin.PropertyEditing.Mac/Controls/RequestResource/RequestResourceView.cs

-3
Original file line numberDiff line numberDiff line change
@@ -26,9 +26,6 @@ internal class RequestResourceView
2626
NSSegmentedControl segmentedControl;
2727
NSButton showPreviewImage;
2828
RequestResourcePanel resourceSelectorPanel;
29-
30-
public NSPopover PopOver { get; internal set; }
31-
3229
private bool showPreview;
3330
public bool ShowPreview
3431
{

Xamarin.PropertyEditing/Properties/Resources.Designer.cs

+27-28
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Xamarin.PropertyEditing/Properties/Resources.resx

+4
Original file line numberDiff line numberDiff line change
@@ -752,4 +752,8 @@
752752
<data name="RemoveVariant" xml:space="preserve">
753753
<value>Remove Variant</value>
754754
</data>
755+
<data name="AddVariation" xml:space="preserve">
756+
<value>Add</value>
757+
<comment>Button text telling the user clicking this will add the variation</comment>
758+
</data>
755759
</root>

0 commit comments

Comments
 (0)