package org.ovirt.engine.ui.userportal.client.views.basic.components; import com.google.gwt.core.client.GWT; import org.ovirt.engine.core.common.businessentities.VM; import org.ovirt.engine.core.common.businessentities.VMStatus; import org.ovirt.engine.core.common.businessentities.vm_pools; import org.ovirt.engine.core.compat.Guid; import org.ovirt.engine.ui.frontend.Message; import org.ovirt.engine.ui.uicommon.UICommand; import org.ovirt.engine.ui.uicommon.models.userportal.UserPortalItemModel; import org.ovirt.engine.ui.uicommon.models.vms.SpiceConsoleModel; import org.ovirt.engine.ui.userportal.client.common.Severity; import org.ovirt.engine.ui.userportal.client.components.ChangeableEdgeVLayout; import org.ovirt.engine.ui.userportal.client.components.GridElement; import org.ovirt.engine.ui.userportal.client.components.UPLabel; import org.ovirt.engine.ui.userportal.client.modalpanels.MessageDialog; import org.ovirt.engine.ui.userportal.client.protocols.ConsoleUtils; import org.ovirt.engine.ui.userportal.client.protocols.Protocol; import org.ovirt.engine.ui.userportal.client.protocols.ProtocolOptionContainer; import org.ovirt.engine.ui.userportal.client.uicommonext.RDPInterfaceImpl; import org.ovirt.engine.ui.userportal.client.uicommonext.SpiceInterfaceImpl; import org.ovirt.engine.ui.userportal.client.util.UserPortalTools; import com.smartgwt.client.types.Alignment; import com.smartgwt.client.types.Cursor; import com.smartgwt.client.widgets.Img; import com.smartgwt.client.widgets.ImgButton; import com.smartgwt.client.widgets.events.ClickEvent; import com.smartgwt.client.widgets.events.ClickHandler; import com.smartgwt.client.widgets.events.DoubleClickEvent; import com.smartgwt.client.widgets.events.DoubleClickHandler; import com.smartgwt.client.widgets.events.MouseOutEvent; import com.smartgwt.client.widgets.events.MouseOutHandler; import com.smartgwt.client.widgets.events.MouseOverEvent; import com.smartgwt.client.widgets.events.MouseOverHandler; import com.smartgwt.client.widgets.layout.HLayout; import com.smartgwt.client.widgets.layout.VLayout; public class VmTvLayout extends VLayout implements GridElement<UserPortalItemModel>, ProtocolOptionContainer { private ChangeableEdgeVLayout mainLayout; private UPLabel vmNameLabel; private Img vmImage; private UPLabel vmStatusLabel; private Guid entityGuid; private ActionButton runButton; private ActionButton shutdownButton; private ActionButton suspendButton; private UPLabel vmImageConsoleBanner; private UserPortalItemModel currentItem; private Img vmImageDisabledMask; private Img vmImagePausedImage; private Protocol selectedProtocol; private static final int VM_IMAGE_WIDTH = 150; private static final int VM_IMAGE_HEIGHT = 120; private static final int VM_IMAGE_BANNER_HEIGHT = 33; private boolean isUp = true; private boolean isSelected = false; private String protocolMessage; public VmTvLayout(final UserPortalItemModel item) { currentItem = item; entityGuid = item.getIsPool() ? ((vm_pools)item.getEntity()).getvm_pool_id() : ((VM)item.getEntity()).getvm_guid(); setMembersMargin(3); String vmID = UserPortalTools.getSafeId(entityGuid.toString()); mainLayout = new ChangeableEdgeVLayout(150, 170, item.IsVmUp() ? "edges/tvlayout" : "edges/tvlayout_down", "png", 8, "vmTvLayout_mainLayout_"); mainLayout.setMembersMargin(5); vmImageConsoleBanner = new UPLabel("vmTvConsoleBanner"); vmImageConsoleBanner.setHeight(VM_IMAGE_BANNER_HEIGHT); vmImageConsoleBanner.setWidth(VM_IMAGE_WIDTH); vmImageConsoleBanner.setBackgroundImage("general/tvlayout_doubleclick_to_console.png"); vmImageConsoleBanner.setContents("Double Click for Console"); vmImageConsoleBanner.setTop(VM_IMAGE_HEIGHT/2 - VM_IMAGE_BANNER_HEIGHT/2); vmImageConsoleBanner.setAlign(Alignment.CENTER); vmImageConsoleBanner.hide(); vmImage = new Img(); vmImage.setWidth(VM_IMAGE_WIDTH); vmImage.setHeight(VM_IMAGE_HEIGHT); vmImage.setCanHover(true); vmImage.addChild(vmImageConsoleBanner); vmImageDisabledMask = new Img("general/tvlayout_disabled_mask.png", VM_IMAGE_WIDTH, VM_IMAGE_HEIGHT); vmImageDisabledMask.hide(); vmImage.addChild(vmImageDisabledMask); vmImagePausedImage = new Img("status/pause_icon.png", 73,81); vmImagePausedImage.setTop(20); vmImagePausedImage.setLeft(39); vmImagePausedImage.hide(); vmImage.addChild(vmImagePausedImage); mainLayout.addMember(vmImage); vmStatusLabel = new UPLabel("vmTvStatusLabel"); vmStatusLabel.setLayoutAlign(Alignment.CENTER); mainLayout.addMember(vmStatusLabel); HLayout actionButtons = new HLayout(5); actionButtons.setLayoutAlign(Alignment.CENTER); actionButtons.setAutoWidth(); runButton = new ActionButton("actions/play.png", 24, 24, item.getIsPool() ? item.getTakeVmCommand() : item.getRunCommand(), item.getIsPool() ? "Take VM" : "Run VM"); runButton.setID(getID() + "_runButton_" + vmID); actionButtons.addMember(runButton); shutdownButton = new ActionButton("actions/stop.png", 24, 24, item.getShutdownCommand(), "Shutdown VM"); shutdownButton.setID(getID() + "_shutdownButton_" + vmID); actionButtons.addMember(shutdownButton); suspendButton = new ActionButton("actions/pause.png", 24, 24, item.getPauseCommand(), "Suspend VM"); suspendButton.setID(getID() + "_suspendButton_" + vmID); actionButtons.addMember(suspendButton); mainLayout.addMember(actionButtons); vmNameLabel = new UPLabel("vmTvNameLabel"); vmNameLabel.setLayoutAlign(Alignment.CENTER); ConsoleUtils.determineDefaultProtocol(this, item); updateValues(item); addMember(vmNameLabel); addMember(mainLayout); setVmImageConsoleEvent(); } private void setVmImageConsoleEvent() { addMouseOverHandler(new MouseOverHandler() { @Override public void onMouseOver(MouseOverEvent event) { if (!isSelected) mainLayout.setStyleName("vmTvLayoutOver"); if (selectedProtocol != null) { if ((selectedProtocol.equals(Protocol.SPICE) && ConsoleUtils.canOpenSpiceConsole(currentItem)) || (selectedProtocol.equals(Protocol.RDP) && ConsoleUtils.canOpenRDPConsole(currentItem))) { vmImage.setCursor(Cursor.HAND); vmImageConsoleBanner.setCursor(Cursor.HAND); vmImageConsoleBanner.show(); } } } }); addMouseOutHandler(new MouseOutHandler() { @Override public void onMouseOut(MouseOutEvent event) { updateRowColor(); if (vmImageConsoleBanner.isVisible()) { vmImage.setCursor(Cursor.DEFAULT); vmImageConsoleBanner.setCursor(Cursor.DEFAULT); vmImageConsoleBanner.hide(); } } }); vmImage.addDoubleClickHandler(new DoubleClickHandler() { @Override public void onDoubleClick(DoubleClickEvent event) { GWT.log("Executing connect to console command"); if (selectedProtocol != null) { switch(selectedProtocol) { case SPICE: if (ConsoleUtils.canOpenSpiceConsole(currentItem)) { currentItem.getDefaultConsole().getConnectCommand().Execute(); } else { if (!ConsoleUtils.isSpiceAvailable()) { Message message = new Message("Error Connecting to " + currentItem.getName(), "This browser does not support SPICE protocol"); MessageDialog errorDialog = new MessageDialog("Not Supported", message, Severity.ERROR); errorDialog.draw(); } } break; case RDP: if (ConsoleUtils.canOpenRDPConsole(currentItem)) { currentItem.getAdditionalConsole().getConnectCommand().Execute(); } else { if (!ConsoleUtils.isRDPAvailable()) { Message message = new Message("Error Connecting to " + currentItem.getName(), "This browser does not support RDP protocol"); MessageDialog errorDialog = new MessageDialog("Not Supported", message, Severity.ERROR); errorDialog.draw(); } } break; } } } }); } public void updateValues(UserPortalItemModel item) { currentItem = item; setEntityStatus(item.getStatus()); setEntityName(item.getName()); if (item.getStatus().equals(VMStatus.Suspended) || item.getStatus().equals(VMStatus.Paused)) { if (!vmImagePausedImage.isVisible()) vmImagePausedImage.show(); } else { if (vmImagePausedImage.isVisible()) vmImagePausedImage.hide(); } updateRowColor(); if (item.IsVmUp() != isUp) { if (item.IsVmUp()) { isUp = true; mainLayout.setEdgeImage("edges/tvlayout", "png"); vmImageDisabledMask.hide(); } else { isUp = false; mainLayout.setEdgeImage("edges/tvlayout_down", "png"); vmImageDisabledMask.show(); } } setEntityImage("os/large/" + item.getOsType().name() + ".png"); updateActionsAvailability(item); } public void updateRowColor() { if (isSelected) mainLayout.setStyleName("vmTvLayoutSelected"); else mainLayout.setStyleName(currentItem.IsVmUp() ? "vmTvLayoutRunning" : "vmTvLayout"); } public void updateActionsAvailability(UserPortalItemModel item) { runButton.setDisabled(item.getIsPool() ? !item.getTakeVmCommand().getIsExecutionAllowed() : !item.getRunCommand().getIsExecutionAllowed()); shutdownButton.setDisabled(!item.getShutdownCommand().getIsExecutionAllowed()); suspendButton.setDisabled(!item.getPauseCommand().getIsExecutionAllowed()); } public void setEntityName(String name) { if (!vmNameLabel.getContents().equals(name)) { GWT.log("Setting VM name to: " + name); vmNameLabel.setContents(name); } } public void setEntityStatus(VMStatus status) { String statusString = statusTranslator(status); if (!vmStatusLabel.getContents().equals(statusString)) { GWT.log("Setting status to: " + statusString); vmStatusLabel.setContents(statusString); } } public void setEntityImage(String imageName) { if (!vmImage.getSrc().equals(imageName)) { GWT.log("Setting image to: " + imageName); vmImage.setSrc(imageName); } } public void select() { isSelected = true; vmStatusLabel.setBaseStyle("vmTvStatusLabelSelected"); mainLayout.setStyleName("vmTvLayoutSelected"); } public void deselect() { isSelected = false; vmStatusLabel.setBaseStyle("vmTvStatusLabel"); updateRowColor(); } class ActionButton extends ImgButton { private String commandName; public ActionButton(String imgName, Integer width, Integer height, final UICommand command, String tooltipTitle) { super(); setSize(width.toString(), height.toString()); setSrc(imgName); //setShowDown(false); setShowRollOver(false); setTooltip(tooltipTitle); setHoverOpacity(75); setHoverStyle("gridToolTipStyle"); setHoverWidth(1); setHoverWrap(false); setHoverDelay(500); commandName = command.getName(); addClickHandler(new ClickHandler() { @Override public void onClick(ClickEvent event) { GWT.log("Executing " + commandName + " command"); for (UICommand uiCommand : currentItem.getCommands()) { if (uiCommand.getName().equals(commandName)) { uiCommand.Execute(); break; } } } }); } @Override public void setDisabled(boolean disabled) { if (getDisabled() != disabled) super.setDisabled(disabled); } } @Override public void setItemId(Object id) { entityGuid = (Guid)id; } @Override public Object getItemId() { return entityGuid; } public void setProtocol(Protocol protocol) { selectedProtocol = protocol; } public Protocol getProtocol() { return selectedProtocol; } public void setProtocolMessage(String message) { protocolMessage = message; } public String getProtocolMessage() { return protocolMessage; } public String statusTranslator(VMStatus status) { switch (status) { case WaitForLaunch: case PoweringUp: case RebootInProgress: case RestoringState: return "Powering Up"; case MigratingFrom: case MigratingTo: case Up: return "Machine is Ready"; case Paused: case Suspended: return "Paused"; case PoweredDown: case PoweringDown: return "Powering Down"; case Unknown: case Unassigned: case NotResponding: case ImageIllegal: return "Not Available"; case SavingState: case ImageLocked: return "Please Wait.."; case Down: return "Machine is Down"; } return null; } }