Eclipse 4 RCP - how to remove Part from application model? - eclipse

I have this utility method which allows easily to change what is shown in specific location of my application.
The problem is it looks more like that the new Part is on top of the old Part (the old Part is not removed and it is still visible under the new Part).
package cz.vutbr.fit.xhriba01.bc.ui;
import org.eclipse.e4.ui.model.application.ui.basic.MPart;
import org.eclipse.e4.ui.model.application.ui.basic.MPartSashContainer;
import org.eclipse.e4.ui.workbench.modeling.EModelService;
import org.eclipse.e4.ui.workbench.modeling.EPartService;
public class UI {
public static final String PART_INSPECTOR_ID = "bc.part.inspector";
public static void changeInspectorView(String partDescriptorId, EPartService partService, EModelService modelService) {
MPart part = partService.createPart(partDescriptorId);
MPart oldPart = partService.findPart(UI.PART_INSPECTOR_ID);
MPartSashContainer parent = (MPartSashContainer) modelService.getContainer(oldPart);
parent.getChildren().remove(oldPart);
part.setElementId(UI.PART_INSPECTOR_ID);
parent.getChildren().add(0, part);
}
}

You should use:
partService.hidePart(oldPart);
to hide the old part (also removes it from the children).
You might also just be able to do:
oldPart.setToBeRendered(false);
but I am not sure that does enough to update the Eclipse internal state.

Related

Create new NetBeans "save as" module

My goal is simple - save the current HTML file in the NetBeans editor with one additional line at the top and bottom of the file, and with the extension of ".h".
This is my first attempt at a NetBeans module, but following some tutorials and research, I got as far as adding an entry to the popup menu when you right-click on an HTML file in the editor. It currently just shows a "Hello World" message:
The code to do that is here:
package ksmiller99.savehtmlasarduinoresource;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JOptionPane;
import org.openide.awt.ActionID;
import org.openide.awt.ActionReference;
import org.openide.awt.ActionRegistration;
import org.openide.util.NbBundle.Messages;
#ActionID(
category = "Edit",
id = "ksmiller99.savehtmlasarduinoresource.SaveHtmlAsArduinoResource"
)
#ActionRegistration(
displayName = "#CTL_SaveHtmlAsArduinoResource"
)
#ActionReference(path = "Editors/text/html/Popup")
#Messages("CTL_SaveHtmlAsArduinoResource=Save as Arduino Resource")
public final class SaveHtmlAsArduinoResource implements ActionListener {
#Override
public void actionPerformed(ActionEvent ev) {
//todo add a line to top and bottom of current file and save with .h extension
JOptionPane.showMessageDialog(null, "Hello Save As World");
}
}
How can I access the contents of the current editor? Would a different approach make more sense?
I'm using NetBeans 12.0, JDK 13, Windows 10.
Use the New Action wizard to create the source code for a Conditionally Enabled action, enabled when User Selects One Node.
In the 2nd wizard panel select File Type Context Menu and choose text/html as content type. If you want your action to appear only in the context menu you can disable Global Menu Item.
You should end up with code like this:
#ActionID(
category = "File",
id = "org.test.TestHtmlAction"
)
#ActionRegistration(
displayName = "#CTL_TestHtmlAction"
)
#ActionReference(path = "Loaders/text/html/Actions", position = 0)
#Messages("CTL_TestHtmlAction=TestHtmlAction")
public final class TestHtmlAction implements ActionListener
{
private final DataObject context;
private static final Logger LOGGER = Logger.getLogger(TestHtmlAction.class.getName());
public TestHtmlAction(DataObject context)
{
this.context = context;
}
#Override
public void actionPerformed(ActionEvent ev)
{
FileObject file = context.getPrimaryFile();
LOGGER.info("context=" + context.getName() + " file.getPath()=" + file.getPath());
}
}
The wizard creates a context aware action, which is enabled only when user selects a single HTML file node. The DataObject parameter gives you the context of the selected node, so you can retrieve the file path etc.

How to retain the state of a treeviewer in Java RCP application?

I have a simple RCP application having couple of wizards out of which one is having a tree viewer. I want to retain the state of the selected item in the tree viewer next time I open that particular view. As of now I have implemented using static variables and its working fine.I want to know how it can be done in a better way?
//Sample Code
private static RepositoryLocationItem lastRepoItemSelected;
Composite parent=new Composite(SWT.NONE)
treeViewer = new TreeViewer(parent);
treeViewer.setContentProvider(new MovingBoxContentProvider());
treeViewer.setLabelProvider(new MovingBoxLabelProvider());
treeViewer.setInput(getInitalInput());
treeViewer.addSelectionChangedListener(new ISelectionChangedListener() {
/* Setting the value of lastRepoItemSelected */
});
if(lastRepoItemSelected !=null)
{
treeViewer.setSelection(new StructuredSelection(lastRepoItemSelected),true);
}
Assuming this is a 3.x style RCP (your view extends ViewPart) you can use the saveState method to save your view state:
#Override
public void saveState(final IMemento memento)
{
// TODO set values in the 'memento'
}
You can then use the init method to restore values from the memento when the view is shown again:
#Override
public void init(final IViewSite site, final IMemento memento)
throws PartInitException
{
super.init(site, memento);
// TODO restore from 'memento'
}
Note: Mementos are persisted across restarts of your RCP so you need to store values in them which are valid in a new instance of the RCP.
Also look at the Eclipse wiki entry for more information.
For a WizardPage you can use the IDialogSettings. You must set this up in your Wizard using something like:
IDialogSettings pluginSettings = Activator.getDefault().getDialogSettings();
IDialogSettings wizardSettings = pluginSettings.getSection("id of your wizard");
if (wizardSettings == null) {
wizardSettings= new DialogSettings("id of your wizard");
pluginSettings.addSection(wizardSettings);
}
setDialogSettings(wizardSettings);
where Activator is your plugin activator class and "name of your wizard" is a id for your wizard (which can be anything as long as it is unique in your plugin).
In your wizard page you can then get the settings with:
IDialogSettings settings = getDialogSettings();
IDialogSettings has lots of methods for saving and restore various sorts of values, such as:
settings.put("key", "string value");
String value = settings.get("key");

How can I modify data from another controller class?

I have a main class (Main.java), two FXML files (FXML1.fxml, FXML2.fxml) and the corresponding controller (FXML1Controller.java, FXML2Controller.java).
In the FXML1.fxml I have two text fields and two buttons.
In the associated controller (FXML1Controller.java) I have declared the text fields and the button as follows:
public TextField textField1;
public TextField textField2;
public Button buttonchange;
public Button buttonOpenWindow;
public void open ()
{
...
stage.show ();
}
public void change ()
{
textField2.setText (textField1.getText ());
}
I type text into textField1. When I click on the buttonChange, then the text should be set in textfield2. Works. It's simple.
When I click the buttonOpen, then a new window opens.
There, I have only one button, but want to do the same.
So something in the way like this:
public void changeFromHere ()
{
FXMLController1 c1 = new FXMLController1 ();
c1.change ();
}
I also know that similar questions have been asked here.
But somehow it does not work the way I want it.
I always get a NullPointerException. For sure. I know.
So I have done the following:
import java.io.IOException;
import java.net.URL;
import java.util.ResourceBundle;
import java.util.logging.Level;
import java.util.logging.Logger;
import javafx.application.Platform;
import javafx.event.ActionEvent;
import javafx.fxml.FXMLLoader;
import javafx.fxml.Initializable;
import javafx.scene.control.Button;
import javafx.scene.layout.Pane;
import javafx.stage.Stage;
...
public class FXML2Controller implements Initializable
{
...
public Button buttonChangeFromHere;
URL location;
FXMLLoader fxmlLoader;
Pane root;
FXMLController1 fc1;
public voidChangeFromHere ()
{
fc1.change ();
}
#Override
public void initialize (URL url, ResourceBundle rb)
{
try
{
location = getClass ().getResource ("FXML1.fxml");
fxmlLoader = new FXMLLoader (location);
root = (Pane) fxmlLoader.load ();
fc1 = (FXMLController1) fxmlLoader.getController ();
} catch (IOException ex)
{
Logger.getLogger (FXML2Controller.class.getName ()) .log (Level.SEVERE, null, ex);
}
}
...
}
Now I can not get a NullPointerException and it should work this way. But nothing happened !?
If I use for testing System.out.println (fc1.textField2.getText ());, then I get the text "Hello", which I have defined in JavaFXSceneBuilder.
If I remove the text in SceneBuilder, then I get "null". Sure. Likewise, I get "null" when I type in the term "Hello" (in textField1) while program is running.
I have also tried to initialize the textfields first in the initialize method. Then I also get always the text "Hello", although I typed "Byebye".
The solutions to similar questions in this forum can not help me.
That's why I put so a similar question again.
This code is also just an example. I can not paste my whole code here. What I really want to do is:
In my program I have a list (listView).
In the list are paths to files that I save as a file. Works fine (In the Main Controller, Main.fxml). There, I have a method public void save (). Now I want to call from another controller class's the save () method. But almost all variables are "null".
But they can't be "null", because the listView shows me the entrys.
I do not think that getter and setter methods are appropriate, because it would be very much redundant code. And I don't want that.
If someone could answer the question how to do it with textfields from example, then I would be grateful.
If it does not work with textfields, it will not work with other components, too:-(.
Thanks in advance.

Disabling toolbar from icePDF viewer

I am trying a sample with icePDF . Everything is working fine but i need to disable the toolbar which appears at the top. i tried few things but its not working. Can some body please help me out with it. Below is my code.
//package XML.test;
package applet;
import java.util.ResourceBundle;
import javax.swing.JFrame;
import javax.swing.JPanel;
import org.icepdf.ri.common.ComponentKeyBinding;
import org.icepdf.ri.common.SwingController;
import org.icepdf.ri.common.SwingViewBuilder;
import org.icepdf.ri.util.PropertiesManager;
import org.icepdf.core.pobjects.fonts.*;
import org.icepdf.core.views.DocumentViewController;
import org.icepdf.core.*;
public class ViewerComponentExample
{
static void buildFrame(String filepath)
{
System.getProperties().put("org.icepdf.core.scaleImages", "false");
System.getProperties().put("org.icepdf.core.imageReference","smoothScaled");
System.getProperties().put("org.icepdf.core.target.dither", "VALUE_DITHER_DISABLE");
System.getProperties().put("org.icepdf.core.target.fractionalmetrics", "VALUE_FRACTIONALMETRICS_OFF");
System.getProperties().put("org.icepdf.core.target.interpolation", "VALUE_INTERPOLATION_NEAREST_ NEIGHBOR");
System.getProperties().put("org.icepdf.core.screen.interpolation", "VALUE_INTERPOLATION_NEAREST_NEIGHBOR");
System.getProperties().put("org.icepdf.core.awtFontLoading","true");
SwingController controller = new SwingController();
PropertiesManager properties = new PropertiesManager(System.getProperties(), ResourceBundle.getBundle(PropertiesManager.DEFAULT_MESSAGE_BUNDLE));
properties.setBoolean(PropertiesManager.PROPERTY_SHOW_TOOLBAR_ANNOTATION, Boolean.FALSE);
properties.setBoolean(PropertiesManager.PROPERTY_SHOW_TOOLBAR_FIT, Boolean.FALSE);
// Build a SwingViewFactory configured with the controller
SwingViewBuilder factory = new SwingViewBuilder(controller);
JPanel viewerComponentPanel = factory.buildViewerPanel();
// add copy keyboard command
ComponentKeyBinding.install(controller, viewerComponentPanel);
// add interactive mouse link annotation support via callback
controller.getDocumentViewController().setAnnotationCallback(
new org.icepdf.ri.common.MyAnnotationCallback(
controller.getDocumentViewController()));
// Use the factory to build a JPanel that is pre-configured
//with a complete, active Viewer UI.
// Create a JFrame to display the panel in
JFrame window = new JFrame("Metrics Wizard Help");
window.getContentPane().add(viewerComponentPanel);
window.pack();
window.setVisible(true);
controller.setPageFitMode(DocumentViewController.PAGE_FIT_WINDOW_WIDTH, false);
controller.openDocument(filepath);
}
public static void main(String args[])
{
String filepath = "C:/Users/vishalt/Workspaces/Eclipse 4.2 Java/htmltopdf/src/XML/output/SCB_TEST.pdf";
buildFrame(filepath);
}
}
private SwingController controller;
controller = new SwingController();
SwingViewBuilder viewBuilder = new SwingViewBuilder(controller, properties);
JPanel panel = viewBuilder.buildViewerPanel();
controller.setToolBarVisible(false);
You have to set the toolbar invisible because icePdf looks in the PDF-document for the property and overwrites your setting with default when there is no document opened!
There are two ways to this.
1) Follow this example to set all the toolbars to false.
http://www.icesoft.org/JForum/posts/list/17673.page#sthash.48ICrL2A.dpbs
2) You can modify or remove the toolbar by editing the source code for SwingViewBuilder.
Here is a link to the code: http://sventon.icesoft.org/svn/repos/repo/show//icepdf/trunk/icepdf/viewer/src/org/icepdf/ri/common/SwingViewBuilder.java?revision=34004
You probably want to comment out lines 481 - 483.
481 JToolBar toolBar = buildCompleteToolBar(embeddableComponent);
482 if (toolBar != null)
483 cp.add(toolBar, BorderLayout.NORTH)
Remove your import for SwingViewBuilder and create your own class with those lines commented out.

GWT TestCase: Simulating clicking a button on my page

I'm using GWT 2.4 with JUnit 4.8.1. When writing my class that extends GWTTestCase, I want to simulate clicking on a button on the page. Currently, in my onModuleLoad method, this button is only a local field ...
public void onModuleLoad() {
final Button submitButton = Button.wrap(Document.get().getElementById(SUBMIT_BUTTON_ID));
...
// Add a handler to send the name to the server
GetHtmlHandler handler = new GetHtmlHandler();
submitButton.addClickHandler(handler);
How do I simulate clicking on this button from the GWTTestCase? Do I have to expose this button as a public member accessor is there a more elegant way to access it? Here is what I have in my test case so far ...
public class GetHtmlTest extends GWTTestCase {
// Entry point class of the GWT application being tested.
private Productplus_gwt productPlusModule;
#Override
public String getModuleName() {
return "com.myco.clearing.productplus.Productplus_gwt";
}
#Before
public void prepareTests() {
productPlusModule = new Productplus_gwt();
productPlusModule.onModuleLoad();
} // setUp
#Test
public void testSuccessEvent() {
// TODO: Simulate clicking on button
} // testSuccessEvent
}
Thanks, - Dave
It can be as easy as buttonElement.click() (or ButtonElement.as(buttonWidget.getElement()).click(), or ButtonElement.as(Document.get().getElementById(SUBMIT_BUTTON_ID)).click())
But remember that a GWTTestCase doesn't run in your own HTML host page, but an empty one, so you'll first have to insert your button within the page before simulating your module's load.
gwt-test-utils seems to be the perfect framework to answer your need. Instead of inheriting from GWTTestCase, extend the gwt-test-utils GwtTest class and implement your click test with the Browser class, like shown in the getting starting guide :
#Test
public void checkClickOnSendMoreThan4chars() {
// Arrange
Browser.fillText(app.nameField, "World");
// Act
Browser.click(app.sendButton);
// Assert
assertTrue(app.dialogBox.isShowing());
assertEquals("", app.errorLabel.getText());
assertEquals("Hello, World!", app.serverResponseLabel.getHTML());
assertEquals("Remote Procedure Call", app.dialogBox.getText());
}
If you want to keep your button private, you'd be able to retrieve it by introspection. But my advice is to make you view's widgets package protected and to write your unit test in the same package so it could access them. It's more convinent and refactoring-friendly.
gwt-test-utils provide introspection convinence. For example, to retrieve the "dialogBox" field which could have been private, you could have do this :
DialogBox dialogBox = GwtReflectionUtils.getPrivateFieldValue(app, "dialogBox");
But note that using GwtReflectionUtils is not mandatory. gwt-test-utils allows you to use ANY java classes in GWT client side tests, without restriction :)
You can do it like this:
YourComposite view = new YourComposite();
RootPanel.get().add(view);
view.getSubmitButton.getElement().<ButtonElement>cast().click();