Working away at the moment but have come up with a small problem in JFace.
I need to have a check box that allows the next button to become active.
Here is the code:
Button btnConfirm = new Button(container, SWT.CHECK);
btnConfirm.addSelectionListener(new SelectionAdapter() {
#Override
public void widgetSelected(SelectionEvent e) {
//missing if statement
setPageComplete(true);
}
});
btnConfirm.setBounds(330, 225, 75, 20);
btnConfirm.setText("Confirm");
What I'm trying to do is to build a menu where someone has to accept the terms and conditions before they can progress beyond a point. The default is to be unchecked but, when the box is checked, the next button will appear; if it is not, then the next button will remain inactive.
Just make the Button final and access it from within the Listener:
final Button btnConfirm = new Button(shell, SWT.CHECK);
btnConfirm.addSelectionListener(new SelectionAdapter()
{
#Override
public void widgetSelected(SelectionEvent e)
{
if (btnConfirm.getSelection())
setPageComplete(true);
else
setPageComplete(false);
}
});
Alternatively, get the Button from the SelectionEvent:
Button btnConfirm = new Button(shell, SWT.CHECK);
btnConfirm.addSelectionListener(new SelectionAdapter()
{
#Override
public void widgetSelected(SelectionEvent e)
{
Button button = (Button) e.widget;
if (button.getSelection())
setPageComplete(true);
else
setPageComplete(false);
}
});
Related
I'm adding a PopUp menu to one of my widgets, a Table. It is not working! I only achieved to make work accelerator shortcuts if they are on top menu bar items, and not in popup context menu items. Why?
This is my code, but the table is inside a Composite which is inside another composite:
membersTable.setMenu(createMembersPopUpMenu(this));
private Menu createMembersPopUpMenu(Composite parent) {
Menu popUpMenu = new Menu(parent);
//Copy
copyMemberItem = new MenuItem(popUpMenu, SWT.PUSH);
copyMemberItem.setText("Copiar Miembro");
copyMemberItem.setAccelerator(SWT.MOD1 + 'C');
copyMemberItem.addSelectionListener(new SelectionAdapter() {
#Override
public void widgetSelected(SelectionEvent e) {
copyMember();
}
});
//Paste
pasteMemberItem = new MenuItem(popUpMenu, SWT.PUSH);
pasteMemberItem.setText("Pegar Miembro");
pasteMemberItem.setAccelerator(SWT.MOD1 + 'V');
pasteMemberItem.addSelectionListener(new SelectionAdapter() {
#Override
public void widgetSelected(SelectionEvent e) {
pasteMember();
}
});
return popUpMenu;
}
I'm getting stuck while building a forum like application which has a vote button.
I have vote up and vote down button for each content which are automatically generated. I want this button to only display the up and down arrow but not any text or label.. how can i find out which button is pressed?
Automated content..
ImageIcon upvote = new ImageIcon(getClass().getResource("vote_up.png"));
ImageIcon downvote = new ImageIcon(getClass().getResource("vote_down.png"));
JButton vote_up = new JButton(upvote);
JButton vote_down = new JButton(downvote);
vote_up.addActionListener(voting);
vote_down.addActionListener(voting);
Action voting = new AbstractAction(){
#Override
public void actionPerformed(ActionEvent e){
//What to do here to find out which button is pressed?
}
};
any help is appreciated.
public void a(){
int crt_cnt = 0;
for(ClassA temp : listofClassA)
{
b(crt_cnt);
crt_cnt++;
}
}
public void b(crt_cnt){
//draw button
}
As from above, I have multiple vote_up and vote_down button created by the b function, how can i differentiate which crt_cnt is the button from?
There are multiple ways you might achieve this
You could...
Simply use the source of the ActionEvent
Action voting = new AbstractAction(){
#Override
public void actionPerformed(ActionEvent e){
if (e.getSource() == vote_up) {
//...
} else if (...) {
//...
}
}
};
This might be okay if you have a reference to the original buttons
You could...
Assign a actionCommand to each button
JButton vote_up = new JButton(upvote);
vote_up.setActionCommand("vote.up");
JButton vote_down = new JButton(downvote);
vote_down .setActionCommand("vote.down");
//...
Action voting = new AbstractAction(){
#Override
public void actionPerformed(ActionEvent e){
if ("vote.up".equals(e.getActionCommand())) {
//...
} else if (...) {
//...
}
}
};
You could...
Take full advantage of the Action API and make indiviual, self contained actions for each button...
public class VoteUpAction extends AbstractAction {
public VoteUpAction() {
putValue(SMALL_ICON, new ImageIcon(getClass().getResource("vote_up.png")));
}
#Override
public void actionPerformed(ActionEvent e) {
// Specific action for up vote
}
}
Then you could simply use
JButton vote_up = new JButton(new VoteUpAction());
//...
Which will configure the button according to the properties of the Action and will trigger it's actionPerformed method when the button is triggered. This way, you know 100% what you should/need to do when the actionPerformed method is called, without any doubts.
Have a closer look at How to Use Actions for more details
You can detect by using the method getSource() of your EventAction
Action voting = new AbstractAction(){
#Override
public void actionPerformed(ActionEvent e){
if (e.getSource() == vote_up ) {
// vote up clicked
} else if (e.getSource() == vote_down){
// vote down clicked
}
}
};
hey thanks for all the help and assistance! I've finally got it! I solved it by
assigning a text on the button, +/- for vote up or down, followed by the content id which i required, then change the font size to 0
vote.setText("+"+thistopic.content.get(crt_cnt).get_id());
vote.setFont(heading.getFont().deriveFont(0.0f));
after that i could easily trace which button is pressed by comparing to the
actionEvent.getActionCommand()
which return the text on the button!
I would wrap the JButton similar to this:
JButton createMyButton(final JPanel panel, final String text,
final boolean upOrDown, final int gridx, final int gridy) {
final JButton button = new JButton();
button.setPreferredSize(new Dimension(80, 50));
final GridBagConstraints gbc = Factories.createGridBagConstraints(gridx,
gridy);
panel.add(button, gbc);
button.addActionListener(new ActionListener() {
#Override
public void actionPerformed(final ActionEvent e) {
myActionPerformed(text, upOrDown);
}
});
return button;
}
You could use an int instead of the text, if more convenient.
I have a Navigator class and a custom DialogBox class which is descended from GridPane.
public DialogBox(final JDialog jdialog) {
Label lblKeyName = new Label("Enter New Key");
Label lblKeyType = new Label("Select Key Type");
TextField txtKeyName = new TextField();
ComboBox cboKeyType = new ComboBox();
txtKeyName.getText();
Button btnOk = new Button("OK");
Button btnCancel = new Button("Cancel");
btnOk.setOnAction(new EventHandler<ActionEvent>() {
#Override
public void handle(ActionEvent event) {
//TODO: Somehow return the values in the ComboBox and TextField
}
});
btnCancel.setOnAction(new EventHandler<ActionEvent>() {
#Override
public void handle(ActionEvent event) {
jdialog.setVisible(false);
}
});
txtKeyName.prefWidth(300);
cboKeyType.prefWidth(300);
this.add(lblKeyName, 0, 0);
this.add(lblKeyType, 0, 1);
this.add(txtKeyName, 1, 0);
this.add(cboKeyType, 1, 1);
this.add(btnOk, 0, 2);
this.add(btnCancel, 1, 2);
}
This is the constructor for my DialogBox.
JFXPanel fxPanel = new JFXPanel();
testBox = new DialogBox(jdialog);
fxPanel.setScene(new Scene(testBox));
jdialog.add(fxPanel);
jdialog.setVisible(true);
How can I retrieve the values in the TextField and ComboBox? I can slightly recall a long ago class where the professor mentioned a technique involving the calling class (Navigator in this case) implementing an Interface and then passing itself to the DialogBox class to retrieve values. Unfortunately I have not found anything and cannot remember how it is done.
Assuming that the dialog is modal, basically, once btnOk or btnCancel button is pressed you need to change some kind of state flag which you can interrogate to determine how the dialog was closed...
// This will also handle the use case where the user presses the "x" button...
private boolean wasCancelled = true;
//...
public boolean wasCancelled() {
return wasCancelled;
}
In you action listeners, you need to set the state appropriately.
btnOk.setOnAction(new EventHandler<ActionEvent>() {
#Override
public void handle(ActionEvent event) {
wasCancelled = false;
jdialog.setVisible(false);
}
});
btnCancel.setOnAction(new EventHandler<ActionEvent>() {
#Override
public void handle(ActionEvent event) {
wasCancelled = true;
jdialog.setVisible(false);
}
});
Now, once the dialog returns, you need to check this flag...
jdialog.add(fxPanel);
jdialog.setVisible(true);
if (!jdialog.wasCancelled()) {
//...
}
You then need to supply "getter" methods to allow a caller to extract the values from the dialog...
public String getKey() {
return txtKeyName.getText();
}
public String getType() {
return cboKeyType.getSelectionModel().getValue();
}
This will mean you will need to create these two fields as instance variables
Is there a standard SWT control that resembles a button which displays an arrow and opens a dropdown menu when pressed and is not a toolbar-only control?
It would be something like this:
It is similar to a combo box control, except that the "button" area would act more similarly to an actual button - its text would not change based on your selection, it would appear depressed when clicked, and the items would be used for actions or navigational purposes instead of for selection. It's also similar to a control available for toolbars, but I need to use it on a regular composite instead.
This is nearly doable simply by using regular button and popup-menu controls - however, I do not believe I can display the arrow next to the text on the button this way. Anyway, since this kind of control seems fairly common, I assumed there would be a standard way to use these two things as one.
I think, this is what you should do get Drop down menu behavior
Create Menu with style SWT.DROP_DOWN
Create MenuItems on Menu
if you want a button
Create a Button with style SWT.ARROW | SWT.DOWN
add SelectionListener
In SelectionListener, Create a Menu with style SWT.POP_UP and position the menu at the button location.
//code
public static void main(String[] args) {
Display display = new Display();
final Shell shell = new Shell(display);
shell.setSize(300, 200);
shell.setText("Button Example");
shell.setLayout(new RowLayout());
/**
*
* Approach1
*
*/
final Composite btnCntrl = new Composite(shell, SWT.BORDER);
btnCntrl.setBackground(display.getSystemColor(SWT.COLOR_WHITE));
btnCntrl.setBackgroundMode(SWT.INHERIT_FORCE);
GridLayoutFactory.fillDefaults().numColumns(2).equalWidth(false).spacing(0, 1).applyTo(btnCntrl);
CLabel lbl = new CLabel(btnCntrl, SWT.NONE);
lbl.setText("Animals");
Button btn = new Button(btnCntrl, SWT.FLAT|SWT.ARROW|SWT.DOWN);
btn.setLayoutData(new GridData(GridData.FILL_VERTICAL));
btn.addSelectionListener(new SelectionAdapter() {
#Override
public void widgetSelected(SelectionEvent e) {
super.widgetSelected(e);
Menu menu = new Menu(shell, SWT.POP_UP);
MenuItem item1 = new MenuItem(menu, SWT.PUSH);
item1.setText("Hare");
MenuItem item2 = new MenuItem(menu, SWT.PUSH);
item2.setText("Fox");
MenuItem item3 = new MenuItem(menu, SWT.PUSH);
item3.setText("Pony");
Point loc = btnCntrl.getLocation();
Rectangle rect = btnCntrl.getBounds();
Point mLoc = new Point(loc.x-1, loc.y+rect.height);
menu.setLocation(shell.getDisplay().map(btnCntrl.getParent(), null, mLoc));
menu.setVisible(true);
}
});
/***
*
*
* Approach 2
*
*/
final Composite btnCntrl2 = new Composite(shell, SWT.BORDER);
btnCntrl2.setBackground(display.getSystemColor(SWT.COLOR_WHITE));
btnCntrl2.setBackgroundMode(SWT.INHERIT_FORCE);
GridLayoutFactory.fillDefaults().numColumns(2).equalWidth(false).spacing(0, 1).applyTo(btnCntrl2);
CLabel lbl2 = new CLabel(btnCntrl2, SWT.NONE);
lbl2.setText("Animals");
Button btn2 = new Button(btnCntrl2, SWT.FLAT|SWT.ARROW|SWT.DOWN);
btn2.setLayoutData(new GridData(GridData.FILL_VERTICAL));
btn2.addSelectionListener(new SelectionAdapter() {
#Override
public void widgetSelected(SelectionEvent e) {
super.widgetSelected(e);
Shell menu = (Shell) btnCntrl2.getData("subshell");
if(menu != null && !menu.isDisposed()){
menu.dispose();
}
menu = new Shell(shell, SWT.NONE);
menu.setLayout(new FillLayout());
Table table = new Table(menu, SWT.FULL_SELECTION);
table.addListener(SWT.MeasureItem, new Listener() {
#Override
public void handleEvent(Event event) {
event.height = 20; //TODO: determine later
}
});
table.addListener(SWT.PaintItem, new Listener() {
#Override
public void handleEvent(Event event) {
Rectangle bounds = event.getBounds();
event.gc.setBackground(event.display.getSystemColor(SWT.COLOR_BLUE));
event.gc.drawLine(bounds.x, bounds.y+bounds.height-1, bounds.x+bounds.width, bounds.y+bounds.height-1);
}
});
TableItem tableItem= new TableItem(table, SWT.NONE);
tableItem.setText(0, "Hare");
TableItem tableItem2= new TableItem(table, SWT.NONE);
tableItem2.setText(0, "Pony" );
TableItem tableItem3= new TableItem(table, SWT.NONE);
tableItem3.setText(0, "Dog");
Point loc = btnCntrl2.getLocation();
Rectangle rect = btnCntrl2.getBounds();
Point mLoc = new Point(loc.x, loc.y+rect.height);
menu.setLocation(shell.getDisplay().map(btnCntrl2.getParent(), null, mLoc));
menu.pack();
menu.setVisible(true);
btnCntrl2.setData("subshell", menu);
}
});
display.addFilter(SWT.MouseDown, new Listener() {
#Override
public void handleEvent(Event event) {
Shell shell = (Shell) btnCntrl2.getData("subshell");
if(shell != null && !shell.getBounds().contains(event.display.map((Control)event.widget, null, new Point(event.x, event.y)))){
shell.dispose();
btnCntrl2.setData("subshell", null);
}
}
});
shell.open();
while (!shell.isDisposed()) {
if (!display.readAndDispatch())
display.sleep();
}
display.dispose();
}
This snippet shows how to use the described widget in a SWT toolbar. You can set the button text by using the item.setText() method.
This question is almost 10 years old, but just in case someone is still looking for a solution (like I just did ;) ):
I achieved a pretty close behaviour of your description using only a Button and a Menu using this approach: http://eclipseo.blogspot.com/2012/07/show-context-menu-programmatically.html
Button button = new Button(parent, SWT.PUSH);
button.setText("Animals");
Menu menu = new Menu(button);
MenuItem item = new MenuItem(menu, SWT.PUSH);
item.setText("hare");
menu.addListener(SWT.Show, new Listener() {
#Override
public void handleEvent(Event event) {
menu.setVisible(true);
}
});
button.addSelectionListener(new SelectionAdapter() {
#Override
public void widgetSelected(SelectionEvent e) {
menu.notifyListeners(SWT.Show, null);
}
});
The result is that the menu is shown when you (left) click on the button.
Bonus: to achieve the expand icon at the end, you can add a unicode character for a down triangle in the button text like so:
button.setText("Animals \u2BC6");
HTH,
Ben
I'm learning JavaFX and this is just a small programming question.
I have 3 buttons in a VBox. And I want to apply the same 3 effects on all buttons after I put them in the Vbox. But when I use a for loop and getChildren() on the VBox, they are returned as 'Nodes'. I can't use the Button.getText() to find out the text of the button.
Is there a way I can getText of a Node? Or maybe convert the current Node to a Button and get the text that way?
VBox vbox = new VBox();
Button option1 = new Button("Single Player");
Button option2 = new Button("Network Player");
Button option3 = new Button("View Rules");
vbox.getChildren().add(option1);
vbox.getChildren().add(option2);
vbox.getChildren().add(option3);
for (final Node button : vbox.getChildren()) {
button.setOnMouseEntered(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent arg0) {
button.setEffect(addEffect(Color.web("#53CFA6"), .8, 10));
}
});
button.setOnMouseExited(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent arg0) {
button.setEffect(addEffect(Color.web("#FF6800"), .8, 10));
}
});
button.setOnMouseClicked(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent arg0) {
button.setEffect(addEffect(Color.web("#E62800"), .8, 10));
//Need to use button.getText()
//Button button; button.getText() works
}
});
}
there is two options:
1. Convert types. Easy, but not safe.
If you sure you wouldn't add other children to this VBox you can just convert Node to Button:
for (Node node : vbox.getChildren()) {
if (node instanceof Button) {
final Button button = (Button) node;
// all your logic
}
2. Use Factory pattern. Best suites, IMHO.
introduce method createButton which will setup button as you need:
private Button createButton(String name) {
final Button button = new Button(name);
button.setOnMouseEntered(...);
button.setOnMouseExited(...);
button.setOnMouseClicked(...);
return button;
}
and you code will look next way:
Button option1 = createButton("Single Player");
Button option2 = createButton("Network Player");
Button option3 = createButton("View Rules");
vbox.getChildren().addAll(option1, option2, option3);
3. Introduce your own Button class. Better if you plan to extend buttons logic.
public void FancyButton extends Button {
public FancyButton(String name) {
super(name);
//handlers logic here
}
}
You can get text from button and assign it to a string variable by this code :-
String Val = ((Button)event.getSource()).getText();