diff --git a/VERSION b/VERSION index 3c80e4f0..e1df5de7 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -1.4.3 \ No newline at end of file +1.4.4 \ No newline at end of file diff --git a/docs/editors/data-list.md b/docs/editors/data-list.md index b4dab1fd..369a43d9 100644 --- a/docs/editors/data-list.md +++ b/docs/editors/data-list.md @@ -259,3 +259,10 @@ For the **List editor**, select **Item Picker**, _maybe configure it with a nice ![Country picker example, using Data List property-editor, with remote XML data source and Item Picker editor](data-list--example-02-countries.png) +### Further reading + +If you are interesting in real-world usage of Data List, here are some articles for further inspiration... + +- [Content Editor defined dropdowns/checkboxlists and radiobuttonlists in Umbraco v8 with Contentment](https://dev.to/timgeyssens/content-editor-defined-dropdowns-checkboxlists-and-radiobuttonlists-in-umbraco-v8-with-contentment-123f) - a post by Tim Geyssens. +- [Umbraco Image Crop Picker using Contentment Data List](https://dev.to/leekelleher/umbraco-image-crop-picker-using-contentment-data-list-5coi) - a post by Lee Kelleher (me). +- [Creating an Author Picker Using Contentment](https://skrift.io/issues/creating-an-author-picker-using-contentment/) - Paul Seal's article for Skrift magazine, June 2021. diff --git a/src/Umbraco.Community.Contentment/DataEditors/Buttons/ButtonsDataListEditor.cs b/src/Umbraco.Community.Contentment/DataEditors/Buttons/ButtonsDataListEditor.cs index ee235940..36dbf391 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/Buttons/ButtonsDataListEditor.cs +++ b/src/Umbraco.Community.Contentment/DataEditors/Buttons/ButtonsDataListEditor.cs @@ -26,7 +26,7 @@ public sealed class ButtonsDataListEditor : IDataListEditor { Key = "defaultIcon", Name = "Default icon", - Description = "Select an icon to be displayed as the default icon, (for when no icon is available).", + Description = "Select an icon to be displayed as the default icon,
(for when no icon is available).", View = IOHelper.ResolveUrl("~/umbraco/views/propertyeditors/listview/icon.prevalues.html"), }, new ConfigurationField diff --git a/src/Umbraco.Community.Contentment/DataEditors/Buttons/buttons.js b/src/Umbraco.Community.Contentment/DataEditors/Buttons/buttons.js index d579d9d0..d55d2c71 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/Buttons/buttons.js +++ b/src/Umbraco.Community.Contentment/DataEditors/Buttons/buttons.js @@ -73,7 +73,9 @@ angular.module("umbraco").controller("Umbraco.Community.Contentment.DataEditors. }); } - $scope.umbProperty.setPropertyActions(vm.propertyActions); + if (vm.propertyActions.length > 0) { + $scope.umbProperty.setPropertyActions(vm.propertyActions); + } } }; diff --git a/src/Umbraco.Community.Contentment/DataEditors/ContentBlocks/ContentBlocksViewHelper.cs b/src/Umbraco.Community.Contentment/DataEditors/ContentBlocks/ContentBlocksViewHelper.cs index 21698303..d330e2ac 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/ContentBlocks/ContentBlocksViewHelper.cs +++ b/src/Umbraco.Community.Contentment/DataEditors/ContentBlocks/ContentBlocksViewHelper.cs @@ -12,7 +12,8 @@ namespace Umbraco.Community.Contentment.DataEditors { internal static class ContentBlocksViewHelper { - private class FakeController : Controller { } + [Core.Composing.HideFromTypeFinder] + private class ContentBlocksFakeController : ControllerBase { protected override void ExecuteCore() { } } private static readonly RazorViewEngine _viewEngine = new RazorViewEngine { @@ -30,9 +31,9 @@ internal static string RenderPartial(string partialName, ViewDataDictionary view { var httpContext = new HttpContextWrapper(HttpContext.Current); - var routeData = new RouteData { Values = { { "controller", nameof(FakeController) } } }; + var routeData = new RouteData { Values = { { "controller", nameof(ContentBlocksFakeController) } } }; - var controllerContext = new ControllerContext(new RequestContext(httpContext, routeData), new FakeController()); + var controllerContext = new ControllerContext(new RequestContext(httpContext, routeData), new ContentBlocksFakeController()); var viewResult = _viewEngine.FindPartialView(controllerContext, partialName, false); diff --git a/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/ExamineDataListSource.cs b/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/ExamineDataListSource.cs index 3c713290..a1df49d1 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/ExamineDataListSource.cs +++ b/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/ExamineDataListSource.cs @@ -6,10 +6,12 @@ using System.Collections.Generic; using System.Linq; using Examine; +using Examine.LuceneEngine.Providers; using Examine.Search; using Umbraco.Core; using Umbraco.Core.IO; using Umbraco.Core.PropertyEditors; +using Umbraco.Examine; using UmbConstants = Umbraco.Core.Constants; namespace Umbraco.Community.Contentment.DataEditors @@ -20,8 +22,41 @@ public sealed class ExamineDataListSource : IDataListSource private readonly IExamineManager _examineManager; private const string _defaultNameField = "nodeName"; - private const string _defaultValueField = "__Key"; - private const string _defaultIconField = "__Icon"; + private const string _defaultValueField = UmbracoExamineIndex.NodeKeyFieldName; + private const string _defaultIconField = UmbracoExamineIndex.IconFieldName; + + private readonly Dictionary _examineFieldConfig = new Dictionary + { + { + Constants.Conventions.ConfigurationFieldAliases.Items, + new[] + { + LuceneIndex.CategoryFieldName, + LuceneIndex.ItemIdFieldName, + LuceneIndex.ItemTypeFieldName, + UmbracoExamineIndex.IconFieldName, + UmbracoExamineIndex.IndexPathFieldName, + UmbracoExamineIndex.NodeKeyFieldName, + UmbracoExamineIndex.PublishedFieldName, + UmbracoExamineIndex.UmbracoFileFieldName, + "createDate", + "creatorID", + "creatorName", + "icon", + "id", + "level", + _defaultNameField, + "nodeType", + "parentID", + "path", + "templateID", + "updateDate", + "urlName", + "writerID", + "writerName", + }.Select(x => new DataListItem { Name = x, Value = x }) + }, + }; public ExamineDataListSource(IExamineManager examineManager) { @@ -74,28 +109,32 @@ public ExamineDataListSource(IExamineManager examineManager) Key = "nameField", Name = "Name Field", Description = "Enter the field name to select the name from the Examine record.", - View = "textstring", + View = IOHelper.ResolveUrl(TextInputDataEditor.DataEditorViewPath), + Config = _examineFieldConfig }, new ConfigurationField { Key = "valueField", Name = "Value Field", Description = "Enter the field name to select the value (key) from the Examine record.", - View = "textstring", + View = IOHelper.ResolveUrl(TextInputDataEditor.DataEditorViewPath), + Config = _examineFieldConfig }, new ConfigurationField { Key = "iconField", Name = "Icon Field", Description = "(optional) Enter the field name to select the icon from the Examine record.", - View = "textstring", + View = IOHelper.ResolveUrl(TextInputDataEditor.DataEditorViewPath), + Config = _examineFieldConfig }, new ConfigurationField { Key = "descriptionField", Name = "Description Field", Description = "(optional) Enter the field name to select the description from the Examine record.", - View = "textstring", + View = IOHelper.ResolveUrl(TextInputDataEditor.DataEditorViewPath), + Config = _examineFieldConfig }, }; diff --git a/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/UmbracoContentPropertiesDataListSource.cs b/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/UmbracoContentPropertiesDataListSource.cs index 7c5423cc..60dd09a8 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/UmbracoContentPropertiesDataListSource.cs +++ b/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/UmbracoContentPropertiesDataListSource.cs @@ -30,7 +30,7 @@ public UmbracoContentPropertiesDataListSource(IContentTypeService contentTypeSer public string Name => "Umbraco Content Properties"; - public string Description => "Populate the data source from a Content Type's properties."; + public string Description => "Populate a data source using a Content Type's properties."; public string Icon => "icon-umbraco"; diff --git a/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/UmbracoImageCropDataListSource.cs b/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/UmbracoImageCropDataListSource.cs index d61c46a0..602f2aff 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/UmbracoImageCropDataListSource.cs +++ b/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/UmbracoImageCropDataListSource.cs @@ -38,7 +38,6 @@ public IEnumerable Fields .Select(x => new DataListItem { Icon = Icon, - Description = x.EditorAlias, Name = x.Name, Value = Udi.Create(UmbConstants.UdiEntityType.DataType, x.Key).ToString(), }); @@ -54,7 +53,6 @@ public IEnumerable Fields Config = new Dictionary { { Constants.Conventions.ConfigurationFieldAliases.Items, items }, - { ShowDescriptionsConfigurationField.ShowDescriptions, Constants.Values.True }, { ShowIconsConfigurationField.ShowIcons, Constants.Values.True }, { Constants.Conventions.ConfigurationFieldAliases.DefaultValue, items.FirstOrDefault()?.Value } } diff --git a/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/UserDefinedDataListSource.cs b/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/UserDefinedDataListSource.cs index 8e6e5c78..4e07a7f5 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/UserDefinedDataListSource.cs +++ b/src/Umbraco.Community.Contentment/DataEditors/DataList/DataSources/UserDefinedDataListSource.cs @@ -33,6 +33,30 @@ public sealed class UserDefinedDataListSource : IDataListSource { "confirmRemoval", Constants.Values.True }, { EnableDevModeConfigurationField.EnableDevMode, Constants.Values.True }, { MaxItemsConfigurationField.MaxItems, 0 }, + { NotesConfigurationField.Notes, @" +
+ Advanced: Paste in the raw JSON? +

If you have copied the raw JSON from the Data List preview panel, .

+

The JSON format must be an array of the Data List item structure.
For example...

+ [ + { + ""name"": ""Ready"", + ""value"": ""value1"", + ""icon"": ""icon-stop-alt color-red"", + ""description"": ""One for the money."" + }, { + ""name"": ""Steady"", + ""value"": ""value2"", + ""icon"": ""icon-stop-alt color-orange"", + ""description"": ""Two for the show."" + }, { + ""name"": ""Go!"", + ""value"": ""value3"", + ""icon"": ""icon-stop-alt color-green"", + ""description"": ""Three to get ready. Now go, cat, go."" + } +] +
" }, }, } }; diff --git a/src/Umbraco.Community.Contentment/DataEditors/DataList/data-list.editor.html b/src/Umbraco.Community.Contentment/DataEditors/DataList/data-list.editor.html index d7fe69a3..e241295e 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/DataList/data-list.editor.html +++ b/src/Umbraco.Community.Contentment/DataEditors/DataList/data-list.editor.html @@ -5,6 +5,8 @@
+
+
diff --git a/src/Umbraco.Community.Contentment/DataEditors/DataList/data-list.editor.js b/src/Umbraco.Community.Contentment/DataEditors/DataList/data-list.editor.js index 300f81c4..0ec7a089 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/DataList/data-list.editor.js +++ b/src/Umbraco.Community.Contentment/DataEditors/DataList/data-list.editor.js @@ -18,6 +18,7 @@ angular.module("umbraco").controller("Umbraco.Community.Contentment.DataEditors. defaultIcon: "icon-stop", enableDevMode: 0, maxItems: 0, + notes: null, }; var config = Object.assign({}, defaultConfig, $scope.model.config); @@ -48,7 +49,10 @@ angular.module("umbraco").controller("Umbraco.Community.Contentment.DataEditors. } }; + vm.notes = config.notes; + vm.add = add; + vm.edit = edit; vm.open = open; vm.remove = remove; @@ -56,11 +60,7 @@ angular.module("umbraco").controller("Umbraco.Community.Contentment.DataEditors. $scope.umbProperty.setPropertyActions([{ labelKey: "contentment_editRawValue", icon: "brackets", - method: function () { - devModeService.editValue($scope.model, function () { - // TODO: [LK:2021-04-13] Ensure that the edits are valid. - }); - } + method: edit }, { labelKey: "clipboard_labelForRemoveAllEntries", icon: "trash", @@ -87,6 +87,12 @@ angular.module("umbraco").controller("Umbraco.Community.Contentment.DataEditors. }; + function edit() { + devModeService.editValue($scope.model, function () { + // NOTE: Any future validation can be done here. + }); + }; + function open(item) { var parts = item.icon.split(" "); diff --git a/src/Umbraco.Community.Contentment/DataEditors/ItemPicker/ItemPickerDataListEditor.cs b/src/Umbraco.Community.Contentment/DataEditors/ItemPicker/ItemPickerDataListEditor.cs index 8c6ace4c..619c1a33 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/ItemPicker/ItemPickerDataListEditor.cs +++ b/src/Umbraco.Community.Contentment/DataEditors/ItemPicker/ItemPickerDataListEditor.cs @@ -45,7 +45,7 @@ public sealed class ItemPickerDataListEditor : IDataListEditor { Key = "defaultIcon", Name = "Default icon", - Description = "Select an icon to be displayed as the default icon, (for when no icon is available).", + Description = "Select an icon to be displayed as the default icon,
(for when no icon is available).", View = IOHelper.ResolveUrl("~/umbraco/views/propertyeditors/listview/icon.prevalues.html"), }, new ConfigurationField diff --git a/src/Umbraco.Community.Contentment/DataEditors/ItemPicker/item-picker.js b/src/Umbraco.Community.Contentment/DataEditors/ItemPicker/item-picker.js index a51783a4..895b8f08 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/ItemPicker/item-picker.js +++ b/src/Umbraco.Community.Contentment/DataEditors/ItemPicker/item-picker.js @@ -97,7 +97,9 @@ angular.module("umbraco").controller("Umbraco.Community.Contentment.DataEditors. }); } - $scope.umbProperty.setPropertyActions(vm.propertyActions); + if (vm.propertyActions.length > 0) { + $scope.umbProperty.setPropertyActions(vm.propertyActions); + } } }; diff --git a/src/Umbraco.Community.Contentment/DataEditors/Notes/notes.html b/src/Umbraco.Community.Contentment/DataEditors/Notes/notes.html index 93926f7b..483c8a87 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/Notes/notes.html +++ b/src/Umbraco.Community.Contentment/DataEditors/Notes/notes.html @@ -3,6 +3,4 @@ - License, v. 2.0. If a copy of the MPL was not distributed with this - file, You can obtain one at https://mozilla.org/MPL/2.0/. --> -
-
-
+
diff --git a/src/Umbraco.Community.Contentment/DataEditors/RadioButtonList/radio-button-list.js b/src/Umbraco.Community.Contentment/DataEditors/RadioButtonList/radio-button-list.js index ddf1ce3d..ae671b78 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/RadioButtonList/radio-button-list.js +++ b/src/Umbraco.Community.Contentment/DataEditors/RadioButtonList/radio-button-list.js @@ -51,7 +51,9 @@ angular.module("umbraco").controller("Umbraco.Community.Contentment.DataEditors. }); } - $scope.umbProperty.setPropertyActions(vm.propertyActions); + if (vm.propertyActions.length > 0) { + $scope.umbProperty.setPropertyActions(vm.propertyActions); + } } }; diff --git a/src/Umbraco.Community.Contentment/DataEditors/Tags/tags.js b/src/Umbraco.Community.Contentment/DataEditors/Tags/tags.js index 1188713c..47c3ef99 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/Tags/tags.js +++ b/src/Umbraco.Community.Contentment/DataEditors/Tags/tags.js @@ -110,7 +110,9 @@ angular.module("umbraco").controller("Umbraco.Community.Contentment.DataEditors. }); } - $scope.umbProperty.setPropertyActions(vm.propertyActions); + if (vm.propertyActions.length > 0) { + $scope.umbProperty.setPropertyActions(vm.propertyActions); + } } }; @@ -150,7 +152,6 @@ angular.module("umbraco").controller("Umbraco.Community.Contentment.DataEditors. }; function keyUp($event, $index) { - console.log("keyUp", $event.keyCode, $index); if ($event.keyCode === 8 || $event.keyCode === 46) { remove($index); } diff --git a/src/Umbraco.Community.Contentment/DataEditors/TemplatedList/templated-list.js b/src/Umbraco.Community.Contentment/DataEditors/TemplatedList/templated-list.js index 564f671d..658ff887 100644 --- a/src/Umbraco.Community.Contentment/DataEditors/TemplatedList/templated-list.js +++ b/src/Umbraco.Community.Contentment/DataEditors/TemplatedList/templated-list.js @@ -63,7 +63,9 @@ angular.module("umbraco").controller("Umbraco.Community.Contentment.DataEditors. }); } - $scope.umbProperty.setPropertyActions(vm.propertyActions); + if (vm.propertyActions.length > 0) { + $scope.umbProperty.setPropertyActions(vm.propertyActions); + } } }; diff --git a/src/Umbraco.Community.Contentment/Properties/VersionInfo.cs b/src/Umbraco.Community.Contentment/Properties/VersionInfo.cs index e55b0e26..50bfcc4b 100644 --- a/src/Umbraco.Community.Contentment/Properties/VersionInfo.cs +++ b/src/Umbraco.Community.Contentment/Properties/VersionInfo.cs @@ -1,5 +1,5 @@ using System.Reflection; [assembly: AssemblyVersion("1.4")] -[assembly: AssemblyFileVersion("1.4.3")] -[assembly: AssemblyInformationalVersion("1.4.3")] +[assembly: AssemblyFileVersion("1.4.4")] +[assembly: AssemblyInformationalVersion("1.4.4")]