Thanks for the framework, it is really good. I have an issue I would like some help with please.
I am using the 1.0.8-preview3 version and using the Eclipse Theme (though I have tried others to no avail).
I have a JTree in a dockable and I am trying to pass the focus on to the tree whenever the dockable gets the focus. I tried adding a CFocusListener (below) which requests the focus however, the focus always seems to remain with the tab label.
Is there something else I should be doing instead?
Thanks
public void focusGained(CDockable dockable) {
if(dockable instanceof DefaultSingleCDockable) {
((DefaultSingleCDockable)dockable).getContentPane().requestFocus();
}
}
public void focusLost(CDockable dockable) { }
};```
The framework also calls “requestFocus” on some components to ensure that the focus does not jump away (the focus system of Swing is not very developer-friendly. Some events are delayed, information outdated, requests ignored…).
What if you do something like this:
public void run(){
((DefaultSingleCDockable)dockable).getContentPane().requestFocus();
}
});```
?
[Edit: you might want to have a look at the source code of "DockController.setFocusedDockable". There you see how these focus-events get fired, but also that the focused component might be changed afterwards again]
Many thanks for your suggestions, works lovely now
Just in case someone else needs this, I changed stop() in DockSelector so that ensureFocusSet is now false which causes ensureFocusSet() be called inline in DockController.setFocusedDockable().
I tried the above suggestions and it works for me in about 80% of the cases.
In 20% of the cases the dockable tab gets the focus back.
Would it be possible to build into the framework a mechanism to focus the content of dockables?
I am not sure what would be the best way to do it.
The framework could remember the lastFocusOwner (like JInternalFrame)
or maybe the dockable could have a method to set the desired focus owner inside it…
There is now an interface “FocusStrategy” that tells the framework which Component of a Dockable to focus. The strategy can be set using “DockController.getFocusController().setStrategy(…)”. Also each AbstractCDockable has a method “setFocusComponent” to set the default component for focusing (CControl set a FocusStrategy that reads this component).
Currently I’m on adding some code to track the last focused Component of each Dockable.
I think the focus mechanism got broken in 1.1.0.p5(a)…
I run the following code in 1.1.0p4 and 1.1.0.p5a.
There are two text fields on each dockable
the top one is supposed to get focus.
In p4 the topField always gets focus in p5a it doesn’t…
kind regards,
MM
package test;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JTextField;
import bibliothek.gui.dock.common.CControl;
import bibliothek.gui.dock.common.CGrid;
import bibliothek.gui.dock.common.DefaultSingleCDockable;
import bibliothek.gui.dock.common.theme.ThemeMap;
public class TestFocus
{
public static void main(String[] args)
{
JFrame frame = new JFrame();
CControl control = new CControl(frame);
control.setTheme(ThemeMap.KEY_ECLIPSE_THEME);
DefaultSingleCDockable red = create(control, "Red", Color.RED);
DefaultSingleCDockable green = create(control, "Green", Color.GREEN);
DefaultSingleCDockable blue = create(control, "Blue", Color.BLUE);
DefaultSingleCDockable black = create(control, "Black", Color.BLACK);
CGrid grid = new CGrid(control);
grid.add(0, 0, 5, 5, red);
grid.add(10, 0, 5, 5, green);
grid.add(10, 5, 5, 5, blue);
grid.add(0, 5, 5, 5, black);
control.getContentArea().deploy(grid);
frame.getContentPane().add(control.getContentArea(), BorderLayout.CENTER);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setSize(new Dimension(600, 600));
frame.setVisible(true);
}
public static DefaultSingleCDockable create(CControl control, String title, Color color)
{
JPanel panel = new JPanel(new BorderLayout());
panel.setOpaque(true);
panel.setBackground(color);
JTextField topField = new JTextField();
panel.add(topField, BorderLayout.NORTH);
panel.add(new JTextField(), BorderLayout.SOUTH);
DefaultSingleCDockable singleDockable = new DefaultSingleCDockable(title, title, panel);
singleDockable.setFocusComponent(topField);
return singleDockable;
}
}
Hm, that’s because I slightly changed the strategy in order to fix this bug.
The JComboBox does not response happy if the focus changes after someone clicks on its (unfocusable, look-and-feel dependent) button. So I added some code that prevents focus transfer if clicking on a Component that is already a child of a Dockable. But in your case that is exactly what should happen… kind of a contradiction.
I’ll think up some solution (it’s going to be ugly) and fix this in the next version.
By now that code is active. Usually the focus falls to the Component on which you clicked with the mouse. The tracking system is only used if you select a Dockable through other means (e.g. closing a Dockable, using the keyboard).
You are clicking onto the tabs? The main issue is, that they are focusable and hence they gain the focus. If you use “ctrl+shift+e” to select another Dockable, then the focus is transferred to one of the textareas.
As a quick workaround you can specify a custom FocusStrategy to prevent that from happening (see code below).
The current behavior is the intended behavior, but I’m no longer sure if this is really good. I think I’ll modify the behavior a bit, it does not make much sense to focus a tab or title, even if the user clicked on it. So in the next version the default behavior and the behavior from the workaround will be almost the same.
Now that is something I’m certain that it exists in 1.1.1p3, especially since I downloaded the zip File just to make sure it does exists. You must be using some older version.
[Edit: or you just wait for 1.1.1p4, which I will upload this weekend, and which already contains the modified behavior]
You’re right, it’s there. Got confused with a few more dependend projects that use different Versions of DockingFrames.
I’ll just wait for 1.1.1p4.
Thank you!