Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

WSDropDown: Changes made to pickers are not always synchronized to dropdown #166

Open
FlowIT-JIT opened this issue Aug 17, 2022 · 2 comments

Comments

@FlowIT-JIT
Copy link
Collaborator

See the following example: https://jsfiddle.net/9zca6kf1/1/

Fit.Events.OnReady(function()
{
	// Create DropDown
	var dd = new Fit.Controls.WSDropDown("WSDropDown1");
	dd.Url("https://fitui.org/demo/GetUsers.php");
	dd.JsonpCallback("JsonpCallback"); // Loading data from foreign domain
	dd.MultiSelectionMode(true);
	dd.Width(400);
	dd.DropDownMaxHeight(150);
	dd.OnRequest(function(sender, eventArgs)
	{
		eventArgs.Request.SetParameter("Parent", eventArgs.Node && eventArgs.Node.Value() || "");
	});
	dd.Render(document.querySelector("#DropDownContainer"));
	
	var btn = new Fit.Controls.Button();
	btn.Type(Fit.Controls.ButtonType.Primary);
	btn.Title("Select TreeView node programmatically");
	btn.OnClick(function()
	{
		var tv = dd.GetTreeView();
		tv.Reload(false, function(sender)
		{
			firstNode = tv.GetChildren()[0];
			firstNode.Selected(true); // Does not synchronize to DropDown
			console.log("Node '" + firstNode.Title() + "' selected: " + firstNode.Selected());
		})
	});
	btn.Render(document.querySelector("#ButtonContainer"));
	
	window.dd = dd;
	window.btn = btn;
});

Click the button to load TreeView data and select the first node. Do NOT open the DropDown control first!
Notice how the selection is not reflected in the DropDown control. Now open the DropDown - this results in TreeView being updated with the selection from the DropDown control (which is empty), so the selection in the TreeView is lost.

The same problem might occur if data returned from the server contain nodes that are preselected. These selections will also not propagate to the DropDown control, and they will be lost when DropDown control is opened.

If we open the DropDown control first, before clicking the button, synchronization works as expected.

This is a minor bug since we would normally use the DropDown instance to change selection:
dd.AddSelection("Title goes here", "Unique Value")

@FlowIT-JIT
Copy link
Collaborator Author

The problem is caused by the fact that synchronization events are wired when WSDropDown assigns a picker for the first time using e.g. me.SetPicker(tree). This happens when the pull down menu is opened. Therefore any interaction with the picker controls prior to opening the pull down menu will not propagate back to the DropDown control.

A quick and dirty solution to this would be to call SetPicker(..) in the WSDropDown's constructor for each picker control to ensure wiring of events like demonstrated below, but this introduces a new bug; the TreeView will load data when rooted, and we don't want data to load unless needed!

image

The solution above will cause TreeView to become rooted and therefore load data:

image

We would need to move the logic responsible for wiring synchronization events in SetPicker(..) so it can be used without rooting the picker in the DOM.

FlowIT-JIT added a commit that referenced this issue Aug 17, 2022
#165: Changes to WSDropDown's value was not synchronized to WSTreeView picker if one of the WSListView pickers (for search and action menu items) was the active picker. This resulted in the previous value being restored when calling wsDropDown.ClearData() and wsDropDown.AutoUpdateSelected() to resolve updated display values for the newly assigned dropdown value. This has now been fixed by ensuring that WSTreeView is always kept up to date with the current selection state in WSDropDown as they happen, rather than "catching up" when WSTreeView is set as the active picker control.

#166: Changes made to selection state via a WSDropDown's picker control directly (e.g. dd.GetTreeView().EnsureData(function(sender) { sender.GetChild("ROOTNODE").Selected(true); });) would not propagate to host control (WSDropDown) unless pull down menu had been opened first, which would set up the necessary synchronization events. This has now been resolved.

Also fixed a bug in WSTreeView where clearing the control with Value("") would add a preselection with an empty value.
@FlowIT-JIT
Copy link
Collaborator Author

FlowIT-JIT commented Aug 17, 2022

The issue has now been resolved.

image

However notice that changes to selection state only propagates to the WSDropDown control if nodes actually exist in the WSTreeView instance. Setting a value or node selection on the WSTreeView instance using Value(..) or SetNodeSelection(..) will not result in this change propagating to the WSDropDown control if the nodes specified does not actually exist (e.g. not loaded yet), but are merely preselections. So make sure data is loaded first:

wsDropDown.GetTreeView().EnsureData(function(sender) { /* Manipulate selection state here */ });

To be determined: Should selection of non-existing nodes be synchronized to DropDown control when assigned via picker control? It works when assigned via DropDown control.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

1 participant