Solution to this problem can be solved by using ViewData and ParentActionViewContext property of class ContrllerContext. ParectActionViewContext is a object that contains the view context information for the parent action method.
Sample psedudo for Parent Block:
public ActionResult Index(ParentBlock currentBlock){
ViewData["ValueToAccesinChild"] = ValueforChild;
....
return View(Model)
}
Sample psedudo for Child Block:
public override ActionResult Index(){
List<string> items = ControllerContext.ParentActionViewContext.ViewData["ValueToAccesinChild"] as List<strings>();
}
Above Higlighted code will work for problem add null checks and other code as per standards.This code focus for the key aspects for solving your problem.
Here is the way i implemented it & it works.However,the 1 issue that i see here is as of now the Parent block only has this one IList property which works for me but if there are multiple IList property then there will be problem.The highlighed code checks for IList<string> property to traverse through the list & returns the list.So if there are multiple Ilist properties in the block ,the return list will include all the values from all the IList Property
Please feel free to reivew & provide feedback if any.
Example
Carousal Block(Parent)
public virtual IList<string> Items { get; set; }
Carousal Item Block(Child)
[SelectMany(SelectionFactoryType = typeof(ItemSelectionFactory))]
public virtual string SelectedItems { get; set; }
Carousal block includes a Content Area for multiple Carousal ITem blocks within which the selected Items selection factory is located.
public IEnumerable<ISelectItem> GetSelections(ExtendedMetadata metadata)
{
var selections = new List<SelectItem>();
var contentRepository = ServiceLocator.Current.GetInstance<IContentRepository>();
var ownerContent = metadata.FindOwnerContent();
var references = contentRepository.GetReferencesToContent(ownerContent.ContentLink, false).FirstOrDefault();
var contentLoader = ServiceLocator.Current.GetInstance<IContentLoader>();
if (contentRepository.TryGet(references.OwnerID, references.OwnerLanguage, out ContentData owner))
{
owner = (ContentData)owner;
}
foreach (var property in owner.Property.Where(x => !x.IsMetaData))
{
if (property.Value is IList<string> list)
{
foreach (var item in list)
{
selections.Insert(0, new SelectItem() { Value = item, Text = item });
}
}
}
return selections;
}
Here's the final output from both the blocks:
Regards.
Hi,
I have the following structure:
Parent Block
public virtual IList<string> Items { get; set; }
Child Block
[SelectOne(SelectionFactoryType = typeof(ItemSelectionFactory))]
public virtual string SelectedItem { get; set; }
I need to create a selection factory that will be populated in Child block(SelectedItem) with values coming from parent block(Items).
For Instance: Parent Block IList values(1,2,3,4) should be populated within Child block selection dropdown
Is there a way to achieve this using the above structure?
Any help is appreciated.
Regards.