I would like to print out the content of a homepage created with Vaadin 14 from a button.
with Vaadin 8 was a solution that unfortunately is no longer applicable:
Button print = new Button("Print This Page");
print.addClickListener(new Button.ClickListener() {
public void buttonClick(ClickEvent event) {
// Print the current page
JavaScript.getCurrent().execute("print();");
}
});
Any Idea how to do this in Vaadin14 please?
In Vaadin 10 and later, you can run arbitrary JavaScript by calling Page::executeJs
UI.getCurrent().getPage().executeJs( … )
There you should be able to call the same print function. See: Executing JavaScript in the Browser.
So in your case, for printing the current page:
UI.getCurrent().getPage().executeJs( "print();" ) ;
Full example in Vaadin 14.0.12, using lambda syntax:
package com.example;
import com.vaadin.flow.component.ClickEvent;
import com.vaadin.flow.component.UI;
import com.vaadin.flow.component.button.Button;
import com.vaadin.flow.component.html.H1;
import com.vaadin.flow.component.orderedlayout.VerticalLayout;
import com.vaadin.flow.router.Route;
/**
* The main view contains a button and a click listener.
*/
#Route ( "" )
public class MainView extends VerticalLayout
{
public MainView ( )
{
this.add( new H1( "Print example" ) );
Button printButton = new Button( "Print…" );
printButton.addClickListener( ( ClickEvent < Button > clickEvent ) ->
{
UI.getCurrent().getPage().executeJs( "print();" );
} );
this.add(printButton);
}
}
Related
I'm calling an obj for my index.js screen like that ...
index.js
import React from 'react';
import { View, Text } from 'react-native';
import ScreenUsers from './ScreenUsers';
const Users = (props) => {
const username = props?.route?.params?.user.map(name => (
name.userDetails.nameUser
));
return (
<Text>{username}</Text>
{ScreenUsers()}
);
}
Until then my index.js works, pull the username, however my index has a component from another screen called ScreenUsers.js where I make a list of users. In this other component that is breaking because it does not return what I want.
ScreenUsers.js
import React from 'react';
import { View, Text } from 'react-native';
function ScreenUsers(props) {
const fullnanme = props?.route?params?.user.users;
return <Text>{fullname}</Text>
}
ScreenUsers have route error
you use ScreenUsers as component not as screen, you can't handle route in this case, if you want to use it as navigation screen you must use navigation read here
and if you want to use it only as component
edit this line {ScreenUsers()} to
//pass prop fullname down
<ScreenUsers fullname={"user name1"} />
//recieve props fullname
function ScreenUsers(props) {
return <Text>{props?.fullname}</Text>
}
if you already use ScreenUsers as screen in navigation and you want also to use it as component you can do something like this
//pass prop route
<ScreenUsers route={{params : {fullname : "user name1"}} />
//recieve props fullname
function ScreenUsers(props) {
return <Text>{props?.route?.params?.fullname}</Text>
}
is this expected behavior?
Clicking 2x on the "set to 'foo'"-Button will cause the innerHTML to become empty.
import java.util.Random;
import com.vaadin.flow.component.button.Button;
import com.vaadin.flow.component.html.Div;
import com.vaadin.flow.router.Route;
#Route("test2")
public class V_Test2 extends Div
{
public V_Test2()
{
Div div = new Div();
add(div);
{
Button button = new Button("set to 'foo'");
button.addClickListener(e -> div.getElement().setProperty("innerHTML", "foo"));
add(button);
}
{
Button button = new Button("set random");
button.addClickListener(e -> div.getElement().setProperty("innerHTML", "bar-" + new Random().nextInt()));
add(button);
}
{
Button button = new Button("set to null");
button.addClickListener(e -> div.getElement().setProperty("innerHTML", null));
add(button);
}
}
}
This is a known bug: https://github.com/vaadin/flow/issues/4644. You can bypass the broken logic by instead using JavaScript to set the innerHMTL value. This would be something along the lines of div.getElement().executeJavaScript("this.innerHTML = $0", "foo");.
I created a basic Vaadin application then added my Domino Jar files.
When I run the application, I get
[com.vaadin.server.ServiceException: java.lang.NoClassDefFoundError: lotus/domino/NotesException]
I've read a bunch of articles that talk about using OSGI etc. Isn't there a simple way to access Domino data from Vaadin without all the plug-ins etc? If not can someone explain why?
This is the calling code
package com.lms.helloDomino;
import javax.servlet.annotation.WebServlet;
import com.lms.service.StarService;
import com.vaadin.annotations.Theme;
import com.vaadin.annotations.VaadinServletConfiguration;
import com.vaadin.server.VaadinRequest;
import com.vaadin.server.VaadinServlet;
import com.vaadin.ui.Button;
import com.vaadin.ui.Label;
import com.vaadin.ui.TextField;
import com.vaadin.ui.UI;
import com.vaadin.ui.VerticalLayout;
import lotus.domino.NotesException;
/**
* This UI is the application entry point. A UI may either represent a browser window
* (or tab) or some part of an HTML page where a Vaadin application is embedded.
* <p>
* The UI is initialized using {#link #init(VaadinRequest)}. This method is intended to be
* overridden to add component to the user interface and initialize non-component functionality.
*/
#Theme("mytheme")
public class MyUI extends UI {
#Override
protected void init(VaadinRequest vaadinRequest) {
StarService myStarService = null;
try
{
myStarService = new StarService();
myStarService.openStarDB();
} catch ( Exception e1 )
{
// TODO Auto-generated catch block
e1.printStackTrace();
}
final VerticalLayout layout = new VerticalLayout();
final TextField name = new TextField();
name.setCaption("Your Domino Name");
name.setValue( myStarService.getNABProfile( "" ).fullName.toString() );
Button button = new Button("Click Me");
button.addClickListener(e -> {
layout.addComponent(new Label("Thanks " + name.getValue()
+ ", it works!"));
});
layout.addComponents(name, button);
setContent(layout);
}
#WebServlet(urlPatterns = "/*", name = "MyUIServlet", asyncSupported = true)
#VaadinServletConfiguration(ui = MyUI.class, productionMode = false)
public static class MyUIServlet extends VaadinServlet {
}
}
Here is the domino code
package com.lms.service;
import lotus.domino.NotesException;
import lotus.domino.Session;
import lotus.domino.NotesFactory;
public class StarService
{
public static Session notesSession = null;
public static Session getNotesSession()
{
if( notesSession == null )
try
{
notesSession = NotesFactory.createSession( "testHostServer", "testUser", "testPassword" );
} catch ( NotesException e )
{
e.printStackTrace();
}
return notesSession;
}
public StarService() throws NotesException
{
System.out.println( "Begin StarService Constructor" );
// Setup the notes connectivity
getNotesSession();
System.out.print( getNotesSession().getUserName() );
System.out.println( "End STARService Constructor" );
}
}
Turns out it was a build path issue. A big thank you to Karsten Lehmann from mindoo.de who helped me figure this out.
I didn't realize when running an Apache web server which serves up the Vaadin application, required my Domino .jar files on it's build path as well. He showed my how to add the .jar files to Apache's as follows:
Double click the Apache server under the servers tab
Click the Open Launch Configuration
Click the Class Path Tab
Highlight User Entries and Add External Jar files.
I've been looking for this off / on for a year now. Can't believe it's finally working!!!
In a Vaadin 8.1.3 app, I have a NativeSelect component on a layout, with a CheckBox next to it. The listener on the checkbox calls setEnabled on the popup-menu (the NativeSelect), passing true or false.
If false, I expected the widget to be dimmed in appearance, per the documentation. And I expected the popup menu to no longer pop up when clicked. Both of these expectations were not met. The widget does not change in appearance whether enabled or not. The widget continues to pop-up a menu when clicked. That's bad.
When enabled is set to false, choosing an item from the menu no longer triggers an event. The listener that responds to a value change on the menu no longer runs. That's good.
Is this a bug on the NativeSelect? The NativeSelect::setEnabled method documentation promises:
… The user can not interact with disabled components, which are shown with a style that indicates the status, usually shaded in light gray color. …
Is there some other way to dim the appearance of the NativeSelect and disable the display of its menu?
In summary, I am looking for three behaviors on a disabled popup menu:
Grayed-out/dimmed appearance
No longer pops up when clicked
Generates no events when clicked
The setEnabled command seems to promise all three bullets but delivers only the last bullet.
I am surprised by this behavior, given that this is a "native" HTML object. The select HTML object is defined to have a disable attribute in both old HTML as well as HTML5. This attribute has both effects I need: alter display, and make un-clickable. See this explanation and this demo of the HTML select widget being disabled.
I filed Issue # 9956.
It's because Vaadin Component interface delivers two methods to adjust component: setEnabled() and setReadOnly() - which you are actually looking for.
Here is my solution for you:
NativeSelect<String> nativeSelect = new NativeSelect<String>() {
#Override
public void setEnabled(boolean enabled)
{
super.setEnabled(enabled);
setReadOnly(!enabled);
if (enabled)
removeStyleName("transparency");
else
addStyleName("transparency");
}};
Add to css:
.transparency {
opacity: 0.5;
}
Right and Wrong
You seem to be wrong about the NativeSelect popping up when clicked if disabled and/or read-only.
You seem to be right about the NativeSelect breaking its contract to display a graying-out or similar visual cue if disabled (“shown with a style that indicates the status, usually shaded in light gray color”).
Example app
Here is a complete example Vaadin 8.1.3/8.1.4 in a single class.
package com.example.vaadin.checkboxexample;
import javax.servlet.annotation.WebServlet;
import com.vaadin.annotations.Theme;
import com.vaadin.annotations.VaadinServletConfiguration;
import com.vaadin.data.HasValue;
import com.vaadin.server.VaadinRequest;
import com.vaadin.server.VaadinServlet;
import com.vaadin.ui.*;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
/**
* This UI is the application entry point. A UI may either represent a browser window
* (or tab) or some part of a html page where a Vaadin application is embedded.
* <p>
* The UI is initialized using {#link #init(VaadinRequest)}. This method is intended to be
* overridden to add component to the user interface and initialize non-component functionality.
*
*/
#Theme ( "mytheme" )
public class MyUI extends UI
{
#Override
protected void init ( VaadinRequest vaadinRequest )
{
// Widgets
List < String > strings = Arrays.asList( "This" , "That" , "The other" , "Yet another" );
// Default
final NativeSelect < String > popupDefault = new NativeSelect( "Default:" , new ArrayList<>(strings) );
popupDefault.setValue( strings.get( 3 ) );
popupDefault.addValueChangeListener( ( HasValue.ValueChangeListener < String > ) valueChangeEvent ->
{ System.out.println( "popupDefault selected: " + valueChangeEvent.getValue( ) ); } );
// Disabled
final NativeSelect < String > popupDisabled = new NativeSelect( "Disabled:" , new ArrayList<>(strings) );
popupDisabled.setValue( strings.get( 3 ) );
popupDisabled.addValueChangeListener( ( HasValue.ValueChangeListener < String > ) valueChangeEvent ->
{ System.out.println( "popupDisabled selected: " + valueChangeEvent.getValue( ) ); } );
popupDisabled.setEnabled( false );
// ReadOnly
final NativeSelect < String > popupReadOnly = new NativeSelect( "ReadOnly:" , new ArrayList<>(strings) );
popupReadOnly.setValue( strings.get( 3 ) );
popupReadOnly.addValueChangeListener( ( HasValue.ValueChangeListener < String > ) valueChangeEvent ->
{ System.out.println( "popupReadOnly selected: " + valueChangeEvent.getValue( ) ); } );
popupReadOnly.setReadOnly( true );
// Disabled and ReadOnly
final NativeSelect < String > popupDisabledAndReadOnly = new NativeSelect( "Disabled & ReadOnly:" , new ArrayList<>(strings) );
popupDisabledAndReadOnly.setValue( strings.get( 3 ) );
popupDisabledAndReadOnly.addValueChangeListener( ( HasValue.ValueChangeListener < String > ) valueChangeEvent ->
{ System.out.println( "popupDisabledAndReadOnly selected: " + valueChangeEvent.getValue( ) ); } );
popupDisabledAndReadOnly.setEnabled( false );
popupDisabledAndReadOnly.setReadOnly( true );
// Layout
final VerticalLayout layout = new VerticalLayout( );
layout.addComponents( popupDefault , popupDisabled , popupReadOnly , popupDisabledAndReadOnly );
setContent( layout );
}
#WebServlet ( urlPatterns = "/*", name = "MyUIServlet", asyncSupported = true )
#VaadinServletConfiguration ( ui = MyUI.class, productionMode = false )
public static class MyUIServlet extends VaadinServlet
{
}
}
Here is a screen-shot when run in Safari Technology Preview browser. Same behaviors seen in Vivaldi browser.
The first popup-menu does indeed popup when clicked; the others three do not. (Good)
Note how at least the second and fourth should appear visually grayed-out but do not. (Bad)
How to increase the Vaadin notification/warning time? I am using Vaadin Valo theme. Nothing from the Book of Vaadin Notifications page helps.
Default Delays
First note that the five types of Notification have different delays by default.
Notification.Type.HUMANIZED_MESSAGEDisplayed until user moves the mouse pointer.
Notification.Type.TRAY_NOTIFICATIONDisplayed until 3 seconds after user moves the mouse pointer.
Notification.Type.WARNING_MESSAGEDisplayed until 1.5 seconds after user moves the mouse pointer.
Notification.Type.ERROR_MESSAGEDisplayed until user clicks on the message. (Delay set to -1 milliseconds)
Notification.Type.ASSISTIVE_NOTIFICATIONDoes nothing for me in Safari on Mac OS X Mountain Lion.
See below for the source code of an example app demonstrating each type.
Controlling Delay
The Notification class has accessors for the delay: getDelayMsec and setDelayMsec.
For example, to set a delay to seven seconds first we must convert to milliseconds.
notification.setDelayMsec( 7 * 1_000 );
Or better yet, replace "magic" numbers with use of the TimeUnit converter. The converter produces only long values, so we must cast to an int to satisfy the Vaadin setter.
notification.setDelayMsec( ( int ) TimeUnit.SECONDS.toMillis( 7 ) );
Beware of one big change in behavior from the default. If setting a positive delay number on an ERROR_MESSAGE, the user need not click to dismiss; the error message disappears after the delay expires after a move of the mouse pointer.
See this code in action in the following example app. Uncomment the line of code calling the setter.
Example App
Here is some Vaadin 7.5.3 code. This class is a complete Vaadin app. Just create a new Vaadin project and replace with this code.
When disabling/enabling the setter, you may need to restart your Vaadin app. (Or buy a license for JRebel to avoid restarts.)
package com.example.vaadinnotifs;
import javax.servlet.annotation.WebServlet;
import com.vaadin.annotations.Theme;
import com.vaadin.annotations.VaadinServletConfiguration;
import com.vaadin.annotations.Widgetset;
import com.vaadin.server.Page;
import com.vaadin.server.VaadinRequest;
import com.vaadin.server.VaadinServlet;
import com.vaadin.ui.Button;
import com.vaadin.ui.Button.ClickEvent;
import com.vaadin.ui.Notification;
import com.vaadin.ui.UI;
import com.vaadin.ui.VerticalLayout;
import java.util.concurrent.TimeUnit;
/**
* By Basil Bourque.
*
* Source code provided under MIT License.
* http://opensource.org/licenses/MIT
*/
#Theme ( "mytheme" )
#Widgetset ( "com.example.vaadinnotifs.MyAppWidgetset" )
#SuppressWarnings ( "serial" )
public class MyUI extends UI
{
#Override
protected void init ( VaadinRequest vaadinRequest ) {
final VerticalLayout layout = new VerticalLayout();
layout.setMargin( true );
layout.setSpacing( true );
setContent( layout );
layout.addComponent( this.makeButton( Notification.Type.HUMANIZED_MESSAGE ) );
layout.addComponent( this.makeButton( Notification.Type.TRAY_NOTIFICATION ) );
layout.addComponent( this.makeButton( Notification.Type.WARNING_MESSAGE ) );
layout.addComponent( this.makeButton( Notification.Type.ERROR_MESSAGE ) );
layout.addComponent( this.makeButton( Notification.Type.ASSISTIVE_NOTIFICATION ) );
}
#WebServlet ( urlPatterns = "/*" , name = "MyUIServlet" , asyncSupported = true )
#VaadinServletConfiguration ( ui = MyUI.class , productionMode = false )
public static class MyUIServlet extends VaadinServlet
{
}
private Button makeButton ( Notification.Type typeArg ) {
// Taking advantage of Java’s nifty Enum capability to generically produce each Button instance.
Button b = new Button( typeArg.name() );
b.setData( typeArg ); // "setData" and "getData" are accessors for a little hiding place for any object you wish to carry with a Vaadin widget.
b.addClickListener( new Button.ClickListener()
{
#Override
public void buttonClick ( ClickEvent event ) {
Notification.Type t = ( Notification.Type ) event.getButton().getData(); // Cast from Object type used by the widget’s hiding place to the `Notification.Type` type we know we used.
Notification notification = new Notification( "This is a Notification message." , t );
//notification.setDelayMsec( ( int ) TimeUnit.SECONDS.toMillis( 7 ) );
Integer delayMillis = notification.getDelayMsec();
String description = "Notification.Type: " + t.name() + " has delay of " + delayMillis + " ms.";
notification.setDescription( description );
notification.show( Page.getCurrent() );
}
} );
return b;
}
}