IDEMPIERE-5570 Zk: Improve readability of code (#1774)

- org.adempiere.webui.dashboard and org.adempiere.webui.desktop package
This commit is contained in:
hengsin 2023-04-11 19:35:38 +08:00 committed by GitHub
parent b5cb64bc92
commit ea6c44b913
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
27 changed files with 789 additions and 234 deletions

View File

@ -47,7 +47,7 @@ import org.zkoss.zk.ui.event.Events;
import org.zkoss.zul.Div; import org.zkoss.zul.Div;
/** /**
* Document Status Indicator * Document Status ({@link MDocumentStatus}) Indicator
*/ */
public class WDocumentStatusIndicator extends Panel implements EventListener<Event> { public class WDocumentStatusIndicator extends Panel implements EventListener<Event> {
private static final long serialVersionUID = -9076405331101242792L; private static final long serialVersionUID = -9076405331101242792L;

View File

@ -16,31 +16,44 @@ package org.adempiere.webui.dashboard;
import org.zkoss.calendar.impl.SimpleCalendarEvent; import org.zkoss.calendar.impl.SimpleCalendarEvent;
/** /**
* * Calendar event for R_Request
* @author Elaine * @author Elaine
*
*/ */
public class ADCalendarEvent extends SimpleCalendarEvent { public class ADCalendarEvent extends SimpleCalendarEvent {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = 2289841014956779967L; private static final long serialVersionUID = 2289841014956779967L;
private int R_Request_ID; private int R_Request_ID;
private int R_RequestType_ID; private int R_RequestType_ID;
/**
* @return R_Request_ID
*/
public int getR_Request_ID() { public int getR_Request_ID() {
return R_Request_ID; return R_Request_ID;
} }
/**
* Set R_Request_ID
* @param request_ID
*/
public void setR_Request_ID(int request_ID) { public void setR_Request_ID(int request_ID) {
R_Request_ID = request_ID; R_Request_ID = request_ID;
} }
/**
* @return R_RequestType_ID
*/
public int getR_RequestType_ID() { public int getR_RequestType_ID() {
return R_RequestType_ID; return R_RequestType_ID;
} }
/**
* Set R_RequestType_ID
* @param requestType_ID
*/
public void setR_RequestType_ID(int requestType_ID) { public void setR_RequestType_ID(int requestType_ID) {
R_RequestType_ID = requestType_ID; R_RequestType_ID = requestType_ID;
} }

View File

@ -72,34 +72,56 @@ import org.zkoss.zul.Timer;
import org.zkoss.zul.Toolbarbutton; import org.zkoss.zul.Toolbarbutton;
/** /**
* * Calendar window
* @author Elaine * @author Elaine
*
*/ */
public class CalendarWindow extends Window implements EventListener<Event>, ITabOnCloseHandler { public class CalendarWindow extends Window implements EventListener<Event>, ITabOnCloseHandler {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = 1576992746053720647L; private static final long serialVersionUID = 1576992746053720647L;
private static final String ON_MOBILE_SET_SELECTED_TAB_ECHO = "onMobileSetSelectedTabEcho"; private static final String ON_MOBILE_SET_SELECTED_TAB_ECHO = "onMobileSetSelectedTabEcho";
private static final String ON_MOVE_DATE_EVENT = "onMoveDate";
private static final String ON_UPDATE_VIEW_EVENT = "onUpdateView";
private static final String ON_MOUSE_OVER_EVENT = "onMouseOver";
private static final String ON_EVENT_UPDATE_EVENT = "onEventUpdate";
private static final String ON_EVENT_EDIT_EVENT = "onEventEdit";
private static final String ON_EVENT_CREATE_EVENT = "onEventCreate";
/** Zk Calendar instance. Center of window. */
private Calendars calendars; private Calendars calendars;
/** Calendar model for {@link #calendars} */
private SimpleCalendarModel scm; private SimpleCalendarModel scm;
/** Re-query button */
private Toolbarbutton btnRefresh; private Toolbarbutton btnRefresh;
/** List of request types */
private Listbox lbxRequestTypes; private Listbox lbxRequestTypes;
/** Pie chart for calendar events. South of window. */
private Image myChart; private Image myChart;
private Button btnCurrentDate, btnSwitchTimeZone; private Button btnCurrentDate, btnSwitchTimeZone;
/** Label for start and end date of current Calendar view */
private Label lblDate; private Label lblDate;
/** button to move Calendar to previous or next page */
private Component divArrowLeft, divArrowRight; private Component divArrowLeft, divArrowRight;
private Span FDOW; private Span FDOW;
/** List to select first day of a week (monday, tuesday, etc). Visible for week and month view. */
private Listbox lbxFDOW; private Listbox lbxFDOW;
/** Tab for Day, Week, 5Day and Month view */
private Component divTabDay, divTabWeek, divTabWeekdays, divTabMonth; private Component divTabDay, divTabWeek, divTabWeekdays, divTabMonth;
/** Message Popup */
private Popup updateMsg; private Popup updateMsg;
/** Content of {@link #updateMsg} */
private Label popupLabel; private Label popupLabel;
/** Timer to close {@link #updateMsg} */
private Timer timer; private Timer timer;
/** Window for event */
private EventWindow eventWin; private EventWindow eventWin;
/**
* Create window content from "zul/calendar/calendar.zul"
* @param scm SimpleCalendarModel
*/
public CalendarWindow(SimpleCalendarModel scm) { public CalendarWindow(SimpleCalendarModel scm) {
super(); super();
@ -112,7 +134,7 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
Component component = Executions.createComponents(ThemeManager.getThemeResource("zul/calendar/calendar.zul"), this, null); Component component = Executions.createComponents(ThemeManager.getThemeResource("zul/calendar/calendar.zul"), this, null);
Borderlayout borderlayout = (Borderlayout) component.getFellow("main"); Borderlayout borderlayout = (Borderlayout) component.getFellow("main");
borderlayout.setStyle("position: absolute"); borderlayout.setStyle("position: relative");
ZKUpdateUtil.setWidth(borderlayout, "100%"); ZKUpdateUtil.setWidth(borderlayout, "100%");
ZKUpdateUtil.setHeight(borderlayout, "100%"); ZKUpdateUtil.setHeight(borderlayout, "100%");
@ -147,10 +169,10 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
lblDate.addEventListener(Events.ON_CREATE, this); lblDate.addEventListener(Events.ON_CREATE, this);
divArrowLeft = component.getFellow("divArrowLeft"); divArrowLeft = component.getFellow("divArrowLeft");
divArrowLeft.addEventListener("onMoveDate", this); divArrowLeft.addEventListener(ON_MOVE_DATE_EVENT, this);
divArrowRight = component.getFellow("divArrowRight"); divArrowRight = component.getFellow("divArrowRight");
divArrowRight.addEventListener("onMoveDate", this); divArrowRight.addEventListener(ON_MOVE_DATE_EVENT, this);
FDOW = (Span) component.getFellow("FDOW"); FDOW = (Span) component.getFellow("FDOW");
FDOW.addEventListener(Events.ON_CREATE, this); FDOW.addEventListener(Events.ON_CREATE, this);
@ -165,16 +187,16 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
} }
divTabDay = component.getFellow("divTabDay"); divTabDay = component.getFellow("divTabDay");
divTabDay.addEventListener("onUpdateView", this); divTabDay.addEventListener(ON_UPDATE_VIEW_EVENT, this);
divTabWeek = component.getFellow("divTabWeek"); divTabWeek = component.getFellow("divTabWeek");
divTabWeek.addEventListener("onUpdateView", this); divTabWeek.addEventListener(ON_UPDATE_VIEW_EVENT, this);
divTabWeekdays = component.getFellow("divTabWeekdays"); divTabWeekdays = component.getFellow("divTabWeekdays");
divTabWeekdays.addEventListener("onUpdateView", this); divTabWeekdays.addEventListener(ON_UPDATE_VIEW_EVENT, this);
divTabMonth = component.getFellow("divTabMonth"); divTabMonth = component.getFellow("divTabMonth");
divTabMonth.addEventListener("onUpdateView", this); divTabMonth.addEventListener(ON_UPDATE_VIEW_EVENT, this);
updateMsg = (Popup) component.getFellow("updateMsg"); updateMsg = (Popup) component.getFellow("updateMsg");
@ -184,10 +206,10 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
this.appendChild(component); this.appendChild(component);
calendars.addEventListener("onEventCreate", this); calendars.addEventListener(ON_EVENT_CREATE_EVENT, this);
calendars.addEventListener("onEventEdit", this); calendars.addEventListener(ON_EVENT_EDIT_EVENT, this);
calendars.addEventListener("onEventUpdate", this); calendars.addEventListener(ON_EVENT_UPDATE_EVENT, this);
calendars.addEventListener("onMouseOver", this); calendars.addEventListener(ON_MOUSE_OVER_EVENT, this);
if (ClientInfo.isMobile()) { if (ClientInfo.isMobile()) {
addCallback(AFTER_PAGE_ATTACHED, t -> afterPageAttached()); addCallback(AFTER_PAGE_ATTACHED, t -> afterPageAttached());
@ -203,6 +225,10 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
} }
} }
/**
* After page attached callback for mobile client. <br/>
* Setup listener for {@link WindowContainer#ON_MOBILE_SET_SELECTED_TAB} event.
*/
private void afterPageAttached() { private void afterPageAttached() {
Component p = getParent(); Component p = getParent();
while (p != null) { while (p != null) {
@ -214,10 +240,15 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
} }
} }
/**
* {@link WindowContainer#ON_MOBILE_SET_SELECTED_TAB} event.<br/>
* Echo {@link #ON_MOBILE_SET_SELECTED_TAB_ECHO} event to redraw {@link #calendars}.
*/
private void onMobileSelected() { private void onMobileSelected() {
Events.echoEvent(ON_MOBILE_SET_SELECTED_TAB_ECHO, this, null); Events.echoEvent(ON_MOBILE_SET_SELECTED_TAB_ECHO, this, null);
} }
@Override
public void onClose(Tabpanel tabPanel){ public void onClose(Tabpanel tabPanel){
//IDEMPIERE-1457: On close, remove calendars away scm //IDEMPIERE-1457: On close, remove calendars away scm
calendars.setModel(null); calendars.setModel(null);
@ -225,6 +256,7 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
tab.close(); tab.close();
} }
@Override
public void onEvent(Event e) throws Exception { public void onEvent(Event e) throws Exception {
String type = e.getName(); String type = e.getName();
@ -246,13 +278,13 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
else if (e.getTarget() == lbxFDOW) else if (e.getTarget() == lbxFDOW)
lbxFDOW.setSelectedIndex(0); lbxFDOW.setSelectedIndex(0);
} }
else if (type.equals("onMoveDate")) { else if (type.equals(ON_MOVE_DATE_EVENT)) {
if (e.getTarget() == divArrowLeft) if (e.getTarget() == divArrowLeft)
divArrowClicked(false); divArrowClicked(false);
else if (e.getTarget() == divArrowRight) else if (e.getTarget() == divArrowRight)
divArrowClicked(true); divArrowClicked(true);
} }
else if (type.equals("onUpdateView")) { else if (type.equals(ON_UPDATE_VIEW_EVENT)) {
String text = String.valueOf(e.getData()); String text = String.valueOf(e.getData());
int days = Msg.getMsg(Env.getCtx(),"Day").equals(text) ? 1: Msg.getMsg(Env.getCtx(),"5Days").equals(text) ? 5: Msg.getMsg(Env.getCtx(),"Week").equals(text) ? 7: 0; int days = Msg.getMsg(Env.getCtx(),"Day").equals(text) ? 1: Msg.getMsg(Env.getCtx(),"5Days").equals(text) ? 5: Msg.getMsg(Env.getCtx(),"Week").equals(text) ? 7: 0;
divTabClicked(days); divTabClicked(days);
@ -278,14 +310,14 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
syncModel(); syncModel();
} }
} }
else if (type.equals("onEventCreate")) { else if (type.equals(ON_EVENT_CREATE_EVENT)) {
if (e instanceof CalendarsEvent) { if (e instanceof CalendarsEvent) {
CalendarsEvent calendarsEvent = (CalendarsEvent) e; CalendarsEvent calendarsEvent = (CalendarsEvent) e;
RequestWindow requestWin = new RequestWindow(calendarsEvent, this); RequestWindow requestWin = new RequestWindow(calendarsEvent, this);
SessionManager.getAppDesktop().showWindow(requestWin); SessionManager.getAppDesktop().showWindow(requestWin);
} }
} }
else if (type.equals("onEventEdit")) { else if (type.equals(ON_EVENT_EDIT_EVENT)) {
if (e instanceof CalendarsEvent) { if (e instanceof CalendarsEvent) {
CalendarsEvent calendarsEvent = (CalendarsEvent) e; CalendarsEvent calendarsEvent = (CalendarsEvent) e;
CalendarEvent calendarEvent = calendarsEvent.getCalendarEvent(); CalendarEvent calendarEvent = calendarsEvent.getCalendarEvent();
@ -300,7 +332,7 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
} }
} }
} }
else if (type.equals("onEventUpdate")) { else if (type.equals(ON_EVENT_UPDATE_EVENT)) {
if (e instanceof CalendarsEvent) if (e instanceof CalendarsEvent)
{ {
CalendarsEvent evt = (CalendarsEvent) e; CalendarsEvent evt = (CalendarsEvent) e;
@ -329,6 +361,9 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
} }
} }
/**
* Update {@link #myChart}
*/
private void syncModel() { private void syncModel() {
Hashtable<String,BigDecimal> ht = new Hashtable<String,BigDecimal>(); Hashtable<String,BigDecimal> ht = new Hashtable<String,BigDecimal>();
@ -362,6 +397,7 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
pieDataset.setValue(name == null ? "" : name, Double.valueOf(size > 0 ? value.doubleValue()/size*100 : 0)); pieDataset.setValue(name == null ? "" : name, Double.valueOf(size > 0 ? value.doubleValue()/size*100 : 0));
} }
//TODO replace with billboard chart
JFreeChart chart = ChartFactory.createPieChart(Msg.getMsg(Env.getCtx(),"EventsAnalysis"), pieDataset, true, true, true); JFreeChart chart = ChartFactory.createPieChart(Msg.getMsg(Env.getCtx(),"EventsAnalysis"), pieDataset, true, true, true);
PiePlot plot = (PiePlot) chart.getPlot(); PiePlot plot = (PiePlot) chart.getPlot();
plot.setForegroundAlpha(0.5f); plot.setForegroundAlpha(0.5f);
@ -377,10 +413,16 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
ht = null; ht = null;
} }
/**
* Refresh model and UI
*/
public void onRefresh() { public void onRefresh() {
btnRefreshClicked(); btnRefreshClicked();
} }
/**
* Refresh model and UI
*/
private void btnRefreshClicked() { private void btnRefreshClicked() {
int R_RequestType_ID = 0; int R_RequestType_ID = 0;
Listitem li = lbxRequestTypes.getSelectedItem(); Listitem li = lbxRequestTypes.getSelectedItem();
@ -411,6 +453,9 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
syncModel(); syncModel();
} }
/**
* Set time zone of {@link #calendars}
*/
private void setTimeZone() private void setTimeZone()
{ {
String alternateTimeZone = MSysConfig.getValue(MSysConfig.CALENDAR_ALTERNATE_TIMEZONE, "Pacific Time=PST", Env.getAD_Client_ID(Env.getCtx())); String alternateTimeZone = MSysConfig.getValue(MSysConfig.CALENDAR_ALTERNATE_TIMEZONE, "Pacific Time=PST", Env.getAD_Client_ID(Env.getCtx()));
@ -424,6 +469,9 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
} }
} }
/**
* Update {@link #lblDate}
*/
private void updateDateLabel() { private void updateDateLabel() {
Date b = calendars.getBeginDate(); Date b = calendars.getBeginDate();
Date e = calendars.getEndDate(); Date e = calendars.getEndDate();
@ -432,12 +480,18 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
lblDate.setValue(sdfV.format(b) + " - " + sdfV.format(e)); lblDate.setValue(sdfV.format(b) + " - " + sdfV.format(e));
} }
/**
* Set {@link #calendars} to current date
*/
private void btnCurrentDateClicked() { private void btnCurrentDateClicked() {
calendars.setCurrentDate(Calendar.getInstance(calendars.getDefaultTimeZone()).getTime()); calendars.setCurrentDate(Calendar.getInstance(calendars.getDefaultTimeZone()).getTime());
updateDateLabel(); updateDateLabel();
syncModel(); syncModel();
} }
/**
* Change {@link #calendars} time zone
*/
private void btnSwitchTimeZoneClicked() { private void btnSwitchTimeZoneClicked() {
Map<?, ?> zone = calendars.getTimeZones(); Map<?, ?> zone = calendars.getTimeZones();
if (!zone.isEmpty()) { if (!zone.isEmpty()) {
@ -449,6 +503,10 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
syncModel(); syncModel();
} }
/**
* Move {@link #calendars} to next or previous page
* @param isNext true for next page, false for previous page
*/
private void divArrowClicked(boolean isNext) { private void divArrowClicked(boolean isNext) {
if (isNext) if (isNext)
calendars.nextPage(); calendars.nextPage();
@ -458,6 +516,10 @@ public class CalendarWindow extends Window implements EventListener<Event>, ITab
syncModel(); syncModel();
} }
/**
* On switching of calendar view (Days, Weeks, etc)
* @param days
*/
private void divTabClicked(int days) { private void divTabClicked(int days) {
if (days > 0) { if (days > 0) {
calendars.setMold("default"); calendars.setMold("default");

View File

@ -66,39 +66,53 @@ import org.zkoss.zul.Label;
import org.zkoss.zul.impl.LabelImageElement; import org.zkoss.zul.impl.LabelImageElement;
/** /**
* Dashboard item: ZK calendar * Dashboard gadget: Zk Calendar. <br/>
* Content created from "zul/calendar/calendar_mini.zul".
* *
* @author Elaine * @author Elaine
* @date November 20, 2008 * @date November 20, 2008
*/ */
public class DPCalendar extends DashboardPanel implements EventListener<Event>, EventHandler { public class DPCalendar extends DashboardPanel implements EventListener<Event>, EventHandler {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = -224914882522997787L; private static final long serialVersionUID = -224914882522997787L;
private static final String ON_MOBILE_SET_SELECTED_TAB_ECHO = "onMobileSetSelectedTabEcho"; private static final String ON_MOBILE_SET_SELECTED_TAB_ECHO = "onMobileSetSelectedTabEcho";
private static final String ON_EVENT_EDIT_EVENT = "onEventEdit";
private static final String ON_EVENT_CREATE_EVENT = "onEventCreate";
private static final String ON_MOVE_DATE_EVENT = "onMoveDate";
private static final String ON_REQUEST_CHANGED_TOPIC = "onRequestChanged";
/** Zk Calendar instance */
private Calendars calendars; private Calendars calendars;
/** Model for {@link #calendars} */
private SimpleCalendarModel scm; private SimpleCalendarModel scm;
/** Button to open Calendar window, to Refresh Calendar */
private LabelImageElement btnCal, btnRefresh; private LabelImageElement btnCal, btnRefresh;
private LabelImageElement btnCurrentDate; private LabelImageElement btnCurrentDate;
/** Label for start and end date of current Calendar view */
private Label lblDate; private Label lblDate;
/** button to move Calendar to previous or next page */
private Component divArrowLeft, divArrowRight; private Component divArrowLeft, divArrowRight;
private static final String ON_REQUEST_CHANGED_TOPIC = "onRequestChanged"; /** Window for event */
private EventWindow eventWin; private EventWindow eventWin;
private WeakReference<Desktop> desktop; private WeakReference<Desktop> desktop;
/** List of Calendar (Request) events */
private ArrayList<ADCalendarEvent> events; private ArrayList<ADCalendarEvent> events;
/** Desktop cleanup listener to call {@link #cleanup()} */
private DesktopCleanup listener; private DesktopCleanup listener;
/** Event handler for R_Request model */
private static RequestEventHandler eventHandler; private static RequestEventHandler eventHandler;
/** Subscriber to {@link IMessageService} for "onRequestChanged" topic */
private static TopicSubscriber subscriber; private static TopicSubscriber subscriber;
private static final CLogger log = CLogger.getCLogger(DPCalendar.class); private static final CLogger log = CLogger.getCLogger(DPCalendar.class);
/**
* Default constructor
*/
public DPCalendar() { public DPCalendar() {
super(); super();
@ -119,15 +133,15 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
lblDate.addEventListener(Events.ON_CREATE, this); lblDate.addEventListener(Events.ON_CREATE, this);
divArrowLeft = component.getFellow("divArrowLeft"); divArrowLeft = component.getFellow("divArrowLeft");
divArrowLeft.addEventListener("onMoveDate", this); divArrowLeft.addEventListener(ON_MOVE_DATE_EVENT, this);
divArrowRight = component.getFellow("divArrowRight"); divArrowRight = component.getFellow("divArrowRight");
divArrowRight.addEventListener("onMoveDate", this); divArrowRight.addEventListener(ON_MOVE_DATE_EVENT, this);
this.appendChild(component); this.appendChild(component);
calendars.addEventListener("onEventCreate", this); calendars.addEventListener(ON_EVENT_CREATE_EVENT, this);
calendars.addEventListener("onEventEdit", this); calendars.addEventListener(ON_EVENT_EDIT_EVENT, this);
createStaticListeners(); createStaticListeners();
@ -144,6 +158,10 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
} }
} }
/**
* After page attached callback for mobile client. <br/>
* Setup listener for {@link WindowContainer#ON_MOBILE_SET_SELECTED_TAB} event.
*/
private void afterPageAttached() { private void afterPageAttached() {
Component p = getParent(); Component p = getParent();
while (p != null) { while (p != null) {
@ -155,10 +173,17 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
} }
} }
/**
* {@link WindowContainer#ON_MOBILE_SET_SELECTED_TAB} event.<br/>
* Echo {@link #ON_MOBILE_SET_SELECTED_TAB_ECHO} event to redraw {@link #calendars}.
*/
private void onMobileSelected() { private void onMobileSelected() {
Events.echoEvent(ON_MOBILE_SET_SELECTED_TAB_ECHO, this, null); Events.echoEvent(ON_MOBILE_SET_SELECTED_TAB_ECHO, this, null);
} }
/**
* Setup {@link #eventHandler} and {@link #subscriber}
*/
private synchronized void createStaticListeners() { private synchronized void createStaticListeners() {
if (eventHandler == null) { if (eventHandler == null) {
eventHandler = new RequestEventHandler(); eventHandler = new RequestEventHandler();
@ -175,6 +200,7 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
} }
} }
@Override
public void onEvent(Event e) throws Exception { public void onEvent(Event e) throws Exception {
String type = e.getName(); String type = e.getName();
@ -190,20 +216,20 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
if (e.getTarget() == lblDate) if (e.getTarget() == lblDate)
updateDateLabel(); updateDateLabel();
} }
else if (type.equals("onMoveDate")) { else if (type.equals(ON_MOVE_DATE_EVENT)) {
if (e.getTarget() == divArrowLeft) if (e.getTarget() == divArrowLeft)
divArrowClicked(false); divArrowClicked(false);
else if (e.getTarget() == divArrowRight) else if (e.getTarget() == divArrowRight)
divArrowClicked(true); divArrowClicked(true);
} }
else if (type.equals("onEventCreate")) { else if (type.equals(ON_EVENT_CREATE_EVENT)) {
if (e instanceof CalendarsEvent) { if (e instanceof CalendarsEvent) {
CalendarsEvent calendarsEvent = (CalendarsEvent) e; CalendarsEvent calendarsEvent = (CalendarsEvent) e;
RequestWindow requestWin = new RequestWindow(calendarsEvent, this); RequestWindow requestWin = new RequestWindow(calendarsEvent, this);
SessionManager.getAppDesktop().showWindow(requestWin); SessionManager.getAppDesktop().showWindow(requestWin);
} }
} }
else if (type.equals("onEventEdit")) { else if (type.equals(ON_EVENT_EDIT_EVENT)) {
if (e instanceof CalendarsEvent) { if (e instanceof CalendarsEvent) {
CalendarsEvent calendarsEvent = (CalendarsEvent) e; CalendarsEvent calendarsEvent = (CalendarsEvent) e;
CalendarEvent calendarEvent = calendarsEvent.getCalendarEvent(); CalendarEvent calendarEvent = calendarsEvent.getCalendarEvent();
@ -220,6 +246,13 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
} }
} }
/**
* TODO move this and ADCalendarEvent to org.adempiere.ui and create unit test for it
* Retrieve events (request) from DB
* @param RequestTypeID
* @param ctx
* @return ADCalendarEvent list
*/
public static ArrayList<ADCalendarEvent> getEvents(int RequestTypeID, Properties ctx) { public static ArrayList<ADCalendarEvent> getEvents(int RequestTypeID, Properties ctx) {
String mode = MSysConfig.getValue(MSysConfig.ZK_DASHBOARD_CALENDAR_REQUEST_DISPLAY_MODE, "CSU", Env.getAD_Client_ID(ctx)); String mode = MSysConfig.getValue(MSysConfig.ZK_DASHBOARD_CALENDAR_REQUEST_DISPLAY_MODE, "CSU", Env.getAD_Client_ID(ctx));
@ -365,7 +398,13 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
return events; return events;
} }
/**
* TODO move to MRequestType
* Get request types from DB
* @param ctx
* @return X_R_RequestType list
*/
public static ArrayList<X_R_RequestType> getRequestTypes(Properties ctx) { public static ArrayList<X_R_RequestType> getRequestTypes(Properties ctx) {
ArrayList<X_R_RequestType> types = new ArrayList<X_R_RequestType>(); ArrayList<X_R_RequestType> types = new ArrayList<X_R_RequestType>();
String sql = "SELECT * " String sql = "SELECT * "
@ -394,6 +433,9 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
return types; return types;
} }
/**
* Refresh model and UI
*/
public void onRefresh() { public void onRefresh() {
btnRefreshClicked(); btnRefreshClicked();
} }
@ -429,15 +471,24 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
calendars.invalidate(); calendars.invalidate();
} }
/**
* Refresh model and UI
*/
private void btnRefreshClicked() { private void btnRefreshClicked() {
refreshModel(); refreshModel();
updateUI(); updateUI();
} }
/**
* Refresh model
*/
private void refreshModel() { private void refreshModel() {
events = getEvents(0, Env.getCtx()); events = getEvents(0, Env.getCtx());
} }
/**
* Update {@link #lblDate}
*/
private void updateDateLabel() { private void updateDateLabel() {
Date b = calendars.getBeginDate(); Date b = calendars.getBeginDate();
Date e = calendars.getEndDate(); Date e = calendars.getEndDate();
@ -446,12 +497,19 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
lblDate.setValue(sdfV.format(b) + " - " + sdfV.format(e)); lblDate.setValue(sdfV.format(b) + " - " + sdfV.format(e));
} }
/**
* Set {@link #calendars} to current date
*/
private void btnCurrentDateClicked() { private void btnCurrentDateClicked() {
calendars.setCurrentDate(Calendar.getInstance(calendars.getDefaultTimeZone()).getTime()); calendars.setCurrentDate(Calendar.getInstance(calendars.getDefaultTimeZone()).getTime());
updateDateLabel(); updateDateLabel();
updateUI(); updateUI();
} }
/**
* Move {@link #calendars} to next or previous page
* @param isNext true for next page, false for previous page
*/
private void divArrowClicked(boolean isNext) { private void divArrowClicked(boolean isNext) {
if (isNext) if (isNext)
calendars.nextPage(); calendars.nextPage();
@ -508,13 +566,16 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
} }
/** /**
* * Perform clean up
*/ */
protected void cleanup() { protected void cleanup() {
EventManager.getInstance().unregister(this); EventManager.getInstance().unregister(this);
desktop = null; desktop = null;
} }
/**
* ITopicSubscriber to post OSGi event from "onRequestChanged" topic
*/
static class TopicSubscriber implements ITopicSubscriber<Map<String, String>> { static class TopicSubscriber implements ITopicSubscriber<Map<String, String>> {
@Override @Override
@ -525,6 +586,9 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
} }
/**
* Event handler for R_Request model
*/
static class RequestEventHandler extends AbstractEventHandler { static class RequestEventHandler extends AbstractEventHandler {
@Override @Override
protected void doHandleEvent(org.osgi.service.event.Event event) { protected void doHandleEvent(org.osgi.service.event.Event event) {
@ -552,6 +616,9 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
} }
} }
/**
* Runnable to post "onRequestChanged" message ({@link IMessageService}) or OSGi event (if {@link IMessageService} not available)
*/
static class RequestRunnable implements Runnable { static class RequestRunnable implements Runnable {
private Map<String, String> message; private Map<String, String> message;
@ -573,10 +640,16 @@ public class DPCalendar extends DashboardPanel implements EventListener<Event>,
} }
} }
/**
* TrxEventListener to call a {@link Runnable} after successful commit of transaction.
*/
static class TrxListener implements TrxEventListener { static class TrxListener implements TrxEventListener {
private Runnable runnable; private Runnable runnable;
/**
* @param runnable
*/
protected TrxListener(Runnable runnable) { protected TrxListener(Runnable runnable) {
this.runnable = runnable; this.runnable = runnable;
} }

View File

@ -45,9 +45,12 @@ import org.zkoss.zk.ui.event.Events;
import org.zkoss.zul.Image; import org.zkoss.zul.Image;
import org.zkoss.zul.Toolbar; import org.zkoss.zul.Toolbar;
/**
* Dashboard gadget for {@link WDocumentStatusPanel}
*/
public class DPDocumentStatus extends DashboardPanel implements EventListener<Event> { public class DPDocumentStatus extends DashboardPanel implements EventListener<Event> {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = 7904122964566112177L; private static final long serialVersionUID = 7904122964566112177L;
private WDocumentStatusPanel statusPanel; private WDocumentStatusPanel statusPanel;
@ -63,6 +66,9 @@ public class DPDocumentStatus extends DashboardPanel implements EventListener<Ev
statusPanel.updateUI(); statusPanel.updateUI();
} }
/**
* Default constructor
*/
public DPDocumentStatus() public DPDocumentStatus()
{ {
super(); super();
@ -94,6 +100,7 @@ public class DPDocumentStatus extends DashboardPanel implements EventListener<Ev
} }
} }
@Override
public void onEvent(Event event) throws Exception { public void onEvent(Event event) throws Exception {
String eventName = event.getName(); String eventName = event.getName();

View File

@ -42,7 +42,7 @@ import org.zkoss.zul.Treerow;
import org.zkoss.zul.Vbox; import org.zkoss.zul.Vbox;
/** /**
* Dashboard item: User favourites - Tree based view organize * Dashboard gadget: User favourites - Tree based view organize
* *
* @author Elaine * @author Elaine
* @author Logilite Technologies - IDEMPIERE-3340 * @author Logilite Technologies - IDEMPIERE-3340
@ -50,14 +50,14 @@ import org.zkoss.zul.Vbox;
*/ */
public class DPFavourites extends DashboardPanel implements EventListener<Event> public class DPFavourites extends DashboardPanel implements EventListener<Event>
{ {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = 7915726855926813700L; private static final long serialVersionUID = 7915726855926813700L;
public static final String FAVOURITE_DROPPABLE = "favourite"; public static final String FAVOURITE_DROPPABLE = "favourite";
/** model for {@link #tree} */
private FavoriteSimpleTreeModel treeModel; private FavoriteSimpleTreeModel treeModel;
private ToolBarButton btnAdd; private ToolBarButton btnAdd;
@ -65,9 +65,12 @@ public class DPFavourites extends DashboardPanel implements EventListener<Event>
private ToolBarButton btnExpand; private ToolBarButton btnExpand;
private ToolBarButton btnAutoLaunch; private ToolBarButton btnAutoLaunch;
/** Favourites menu tree */
private Tree tree; private Tree tree;
// /**
* Default constructor
*/
public DPFavourites() public DPFavourites()
{ {
super(); super();
@ -134,6 +137,10 @@ public class DPFavourites extends DashboardPanel implements EventListener<Event>
this.appendChild(toolbar); this.appendChild(toolbar);
} // DPFavourites } // DPFavourites
/**
* Create favourite tree panel
* @return Box
*/
private Box createFavoritePanel() private Box createFavoritePanel()
{ {
tree = new Tree(); tree = new Tree();
@ -155,7 +162,7 @@ public class DPFavourites extends DashboardPanel implements EventListener<Event>
} // createFavoritePanel } // createFavoritePanel
/** /**
* Creating Tree structure * Create Tree model ({@link #treeModel})
*/ */
public void initTreeModel() public void initTreeModel()
{ {
@ -165,6 +172,7 @@ public class DPFavourites extends DashboardPanel implements EventListener<Event>
/** /**
* Event Like open Menu Window, Expand/Collapse Node, Add node into Tree * Event Like open Menu Window, Expand/Collapse Node, Add node into Tree
*/ */
@Override
public void onEvent(Event event) public void onEvent(Event event)
{ {
String eventName = event.getName(); String eventName = event.getName();
@ -201,6 +209,9 @@ public class DPFavourites extends DashboardPanel implements EventListener<Event>
} }
} // onEvent } // onEvent
/**
* Open {@link LoginOpenSequenceDialog}
*/
private void doLoginOpenSeq() private void doLoginOpenSeq()
{ {
LoginOpenSequenceDialog dialog = new LoginOpenSequenceDialog(Env.getAD_User_ID(Env.getCtx())); LoginOpenSequenceDialog dialog = new LoginOpenSequenceDialog(Env.getAD_User_ID(Env.getCtx()));
@ -211,6 +222,7 @@ public class DPFavourites extends DashboardPanel implements EventListener<Event>
/** /**
* Add or Edit folder * Add or Edit folder
* @param isAddFolder
*/ */
private void doFolderOpr(boolean isAddFolder) private void doFolderOpr(boolean isAddFolder)
{ {
@ -240,6 +252,10 @@ public class DPFavourites extends DashboardPanel implements EventListener<Event>
} }
} // doExpandCollapseAll } // doExpandCollapseAll
/**
* @param tree
* @return Current selected MTreeNode
*/
public static MTreeNode getCurrentSelectedTreeNode(Tree tree) public static MTreeNode getCurrentSelectedTreeNode(Tree tree)
{ {
Treeitem selItem = tree.getSelectedItem(); Treeitem selItem = tree.getSelectedItem();
@ -252,13 +268,17 @@ public class DPFavourites extends DashboardPanel implements EventListener<Event>
return (MTreeNode) dtn.getData(); return (MTreeNode) dtn.getData();
} // getCurrentSelectedTreeNode } // getCurrentSelectedTreeNode
/**
* @param tree
* @return Current selected Node_ID
*/
public static int getCurrentSelectedNodeID(Tree tree) public static int getCurrentSelectedNodeID(Tree tree)
{ {
return getCurrentSelectedTreeNode(tree).getNode_ID(); return getCurrentSelectedTreeNode(tree).getNode_ID();
} // getCurrentSelectedNodeID } // getCurrentSelectedNodeID
/** /**
* Insert Node into Tree it's contains only Menu type node, Dragged from Menu Tab. * Insert Node (Menu type node) into Tree, Dragged from Menu Tab.
* *
* @param menuID - AD_Menu_ID * @param menuID - AD_Menu_ID
* @param parentNodeID - Parent AD_Favorite_Node_ID * @param parentNodeID - Parent AD_Favorite_Node_ID
@ -276,7 +296,7 @@ public class DPFavourites extends DashboardPanel implements EventListener<Event>
} // insertMenuInTree } // insertMenuInTree
/** /**
* Add Node in Tree view * Add Node into Tree view
* *
* @param treeModel - FavoriteSimpleTreeModel * @param treeModel - FavoriteSimpleTreeModel
* @param tree - Tree * @param tree - Tree

View File

@ -17,17 +17,19 @@ import org.adempiere.webui.util.ZKUpdateUtil;
import org.zkoss.zul.Iframe; import org.zkoss.zul.Iframe;
/** /**
* Dashboard item: Google calendar * Dashboard gadget: Google calendar
* @author Elaine * @author Elaine
* @date November 20, 2008 * @date November 20, 2008
*/ */
public class DPGoogleCalendar extends DashboardPanel { public class DPGoogleCalendar extends DashboardPanel {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = -6420016898259232438L; private static final long serialVersionUID = -6420016898259232438L;
/**
* Default constructor
*/
public DPGoogleCalendar() public DPGoogleCalendar()
{ {
super(); super();

View File

@ -17,27 +17,31 @@ package org.adempiere.webui.dashboard;
import org.adempiere.webui.panel.MenuTreePanel; import org.adempiere.webui.panel.MenuTreePanel;
/** /**
* Dashboard item: Menu Tree * Dashboard gadget: Menu Tree
* @author Elaine * @author Elaine
* @date July 31, 2012 * @date July 31, 2012
*/ */
public class DPMenuTree extends DashboardPanel { public class DPMenuTree extends DashboardPanel {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = -3095921038206382907L; private static final long serialVersionUID = -3095921038206382907L;
private MenuTreePanel menuTreePanel; private MenuTreePanel menuTreePanel;
/**
* Default constructor
*/
public DPMenuTree() public DPMenuTree()
{ {
super(); super();
menuTreePanel = new MenuTreePanel(this); menuTreePanel = new MenuTreePanel(this);
this.appendChild(menuTreePanel);
} }
/**
* @return {@link MenuTreePanel}
*/
public MenuTreePanel getMenuTreePanel() public MenuTreePanel getMenuTreePanel()
{ {
return menuTreePanel; return menuTreePanel;

View File

@ -24,7 +24,7 @@ import org.zkoss.zk.ui.Executions;
import org.zkoss.zk.ui.util.Clients; import org.zkoss.zk.ui.util.Clients;
/** /**
* Dashboard item: Performance Indicators * Dashboard gadget: Performance Indicators
* @author Elaine * @author Elaine
* @date November 20, 2008 * @date November 20, 2008
*/ */
@ -36,6 +36,7 @@ public class DPPerformance extends DashboardPanel {
/** performance chart panel */ /** performance chart panel */
private WPAPanel paPanel; private WPAPanel paPanel;
/** {@link MGoal} performance records */
private MGoal[] performanceData; private MGoal[] performanceData;
/** /**

View File

@ -53,31 +53,37 @@ import org.zkoss.zul.Toolbar;
import org.zkoss.zul.Vbox; import org.zkoss.zul.Vbox;
/** /**
* Dashboard item: Recent Items * Dashboard gadget: Recent Items
* @author Carlos Ruiz / GlobalQSS * @author Carlos Ruiz / GlobalQSS
* @date January 27, 2012 * @date January 27, 2012
*/ */
public class DPRecentItems extends DashboardPanel implements EventListener<Event>, EventHandler { public class DPRecentItems extends DashboardPanel implements EventListener<Event>, EventHandler {
private static final String AD_RECENT_ITEM_ID_ATTR = "AD_RecentItem_ID";
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = 662950038476166515L; private static final long serialVersionUID = 662950038476166515L;
/** Recent item link ({@link A}) attribute to store AD_RecentItem_ID value */
private static final String AD_RECENT_ITEM_ID_ATTR = "AD_RecentItem_ID";
/** Droppable identifier */
public static final String DELETE_RECENTITEMS_DROPPABLE = "deleteRecentItems"; public static final String DELETE_RECENTITEMS_DROPPABLE = "deleteRecentItems";
private static TopicSubscriber topicSubscriber; private static TopicSubscriber topicSubscriber;
private Box bxRecentItems; private Box bxRecentItems;
/** Login user id */
private int AD_User_ID; private int AD_User_ID;
private WeakReference<Desktop> desktop; private WeakReference<Desktop> desktop;
/** Desktop cleanup listener to call {@link #cleanup()} */
private DesktopCleanup listener; private DesktopCleanup listener;
/**
* Default constructor
*/
public DPRecentItems() public DPRecentItems()
{ {
super(); super();
@ -145,11 +151,17 @@ public class DPRecentItems extends DashboardPanel implements EventListener<Event
}; };
} }
/**
* Perform clean up
*/
protected void cleanup() { protected void cleanup() {
EventManager.getInstance().unregister(this); EventManager.getInstance().unregister(this);
desktop = null; desktop = null;
} }
/**
* Setup {@link #topicSubscriber}
*/
private static synchronized void createTopicSubscriber() { private static synchronized void createTopicSubscriber() {
if (topicSubscriber == null) { if (topicSubscriber == null) {
topicSubscriber = new TopicSubscriber(); topicSubscriber = new TopicSubscriber();
@ -162,7 +174,7 @@ public class DPRecentItems extends DashboardPanel implements EventListener<Event
} }
/** /**
* Make Recent Item remove persistent * Remove recent item record from DB
* @param AD_RecentItem_ID Recent Item ID * @param AD_RecentItem_ID Recent Item ID
* @return true if updated * @return true if updated
*/ */
@ -175,6 +187,7 @@ public class DPRecentItems extends DashboardPanel implements EventListener<Event
} }
} }
@Override
public void onEvent(Event event) public void onEvent(Event event)
{ {
Component comp = event.getTarget(); Component comp = event.getTarget();
@ -200,6 +213,10 @@ public class DPRecentItems extends DashboardPanel implements EventListener<Event
} }
} }
/**
* Handle onClick event from recent item link/button
* @param comp Component
*/
private void doOnClick(Component comp) { private void doOnClick(Component comp) {
if (comp instanceof A) if (comp instanceof A)
{ {
@ -227,6 +244,9 @@ public class DPRecentItems extends DashboardPanel implements EventListener<Event
} }
} }
/**
* Reload from DB
*/
private synchronized void refresh() { private synchronized void refresh() {
// Please review here - is throwing NPE in some cases when user push repeatedly the refresh button // Please review here - is throwing NPE in some cases when user push repeatedly the refresh button
List<?> childs = bxRecentItems.getChildren(); List<?> childs = bxRecentItems.getChildren();
@ -276,6 +296,10 @@ public class DPRecentItems extends DashboardPanel implements EventListener<Event
} }
/**
* Remove recent item link from {@link #bxRecentItems} and DB
* @param btn {@link A}
*/
private void removeLink(A btn) { private void removeLink(A btn) {
String value = (String) btn.getAttribute(AD_RECENT_ITEM_ID_ATTR); String value = (String) btn.getAttribute(AD_RECENT_ITEM_ID_ATTR);
@ -288,6 +312,9 @@ public class DPRecentItems extends DashboardPanel implements EventListener<Event
} }
} }
/**
* @return icon font class or icon image url
*/
private String getIconFile() { private String getIconFile() {
if (ThemeManager.isUseFontIconForImage()) if (ThemeManager.isUseFontIconForImage())
return "z-icon-Window"; return "z-icon-Window";
@ -311,7 +338,7 @@ public class DPRecentItems extends DashboardPanel implements EventListener<Event
} }
/** /**
* * Update {@link #desktop} reference and setup {@link #listener}
*/ */
protected void updateDesktopReference() { protected void updateDesktopReference() {
if ((desktop == null || desktop.get() == null) || (desktop.get() != null && desktop.get() != getDesktop())) { if ((desktop == null || desktop.get() == null) || (desktop.get() != null && desktop.get() != getDesktop())) {
@ -364,7 +391,14 @@ public class DPRecentItems extends DashboardPanel implements EventListener<Event
return true; return true;
} }
/**
* {@link ITopicSubscriber} for "onRecentItemChanged" topic. <br/>
* Call {@link MRecentItem#postOnChangedEvent(int)}.
*/
static class TopicSubscriber implements ITopicSubscriber<Integer> { static class TopicSubscriber implements ITopicSubscriber<Integer> {
/**
* @param message AD_User_ID
*/
@Override @Override
public void onMessage(Integer message) { public void onMessage(Integer message) {
MRecentItem.postOnChangedEvent(message); MRecentItem.postOnChangedEvent(message);

View File

@ -49,24 +49,33 @@ import org.zkoss.zul.Panelchildren;
import org.zkoss.zul.Toolbar; import org.zkoss.zul.Toolbar;
import org.zkoss.zul.Vbox; import org.zkoss.zul.Vbox;
/**
* Dashboard gadget: running background jobs (Run As Job in Process Dialog).
*/
public class DPRunningJobs extends DashboardPanel implements EventListener<Event>, EventHandler { public class DPRunningJobs extends DashboardPanel implements EventListener<Event>, EventHandler {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = -8515643315156488709L; private static final long serialVersionUID = -8515643315156488709L;
/** Job link ({@link A}) attribute to store AD_PInstance_ID value */
private static final String AD_PINSTANCE_ID_ATTR = "AD_PInstance_ID"; private static final String AD_PINSTANCE_ID_ATTR = "AD_PInstance_ID";
private static TopicSubscriber topicSubscriber; private static TopicSubscriber topicSubscriber;
private Box bxJobs; private Box bxJobs;
/** Login user id */
private int AD_User_ID; private int AD_User_ID;
private WeakReference<Desktop> desktop; private WeakReference<Desktop> desktop;
/** Desktop cleanup listener to call {@link #cleanup()} */
private DesktopCleanup listener; private DesktopCleanup listener;
/**
* Default constructor
*/
public DPRunningJobs() public DPRunningJobs()
{ {
super(); super();
@ -114,12 +123,18 @@ public class DPRunningJobs extends DashboardPanel implements EventListener<Event
}; };
} }
/**
* Perform clean up
*/
protected void cleanup() protected void cleanup()
{ {
EventManager.getInstance().unregister(this); EventManager.getInstance().unregister(this);
desktop = null; desktop = null;
} }
/**
* Setup {@link #topicSubscriber}
*/
private static synchronized void createTopicSubscriber() private static synchronized void createTopicSubscriber()
{ {
if (topicSubscriber == null) { if (topicSubscriber == null) {
@ -142,6 +157,10 @@ public class DPRunningJobs extends DashboardPanel implements EventListener<Event
doOnClick(comp); doOnClick(comp);
} }
/**
* Handle onClick event from Job link/button
* @param comp Component
*/
private void doOnClick(Component comp) private void doOnClick(Component comp)
{ {
if (comp instanceof A) if (comp instanceof A)
@ -166,6 +185,9 @@ public class DPRunningJobs extends DashboardPanel implements EventListener<Event
} }
} }
/**
* Reload from DB
*/
private synchronized void refresh() private synchronized void refresh()
{ {
// Please review here - is throwing NPE in some cases when user push repeatedly the refresh button // Please review here - is throwing NPE in some cases when user push repeatedly the refresh button
@ -197,6 +219,10 @@ public class DPRunningJobs extends DashboardPanel implements EventListener<Event
} }
} }
/**
* @param AD_User_ID
* @return List of running background jobs for AD_User_ID
*/
public static List<MPInstance> getRunningJobForUser(int AD_User_ID) public static List<MPInstance> getRunningJobForUser(int AD_User_ID)
{ {
List<MPInstance> pis = new Query(Env.getCtx(), MPInstance.Table_Name, "Coalesce(AD_User_ID,0)=? AND IsProcessing='Y' AND IsRunAsJob='Y'", null) List<MPInstance> pis = new Query(Env.getCtx(), MPInstance.Table_Name, "Coalesce(AD_User_ID,0)=? AND IsProcessing='Y' AND IsRunAsJob='Y'", null)
@ -224,7 +250,7 @@ public class DPRunningJobs extends DashboardPanel implements EventListener<Event
} }
/** /**
* * Update {@link #desktop} reference and setup {@link #listener}
*/ */
protected void updateDesktopReference() protected void updateDesktopReference()
{ {
@ -280,7 +306,14 @@ public class DPRunningJobs extends DashboardPanel implements EventListener<Event
return true; return true;
} }
/**
* {@link ITopicSubscriber} for "onRunningJobChanged" topic. <br/>
* Call {@link MPInstance#postOnChangedEvent(int)}.
*/
static class TopicSubscriber implements ITopicSubscriber<Integer> { static class TopicSubscriber implements ITopicSubscriber<Integer> {
/**
* @param message AD_User_ID
*/
@Override @Override
public void onMessage(Integer message) { public void onMessage(Integer message) {
MPInstance.postOnChangedEvent(message); MPInstance.postOnChangedEvent(message);

View File

@ -41,17 +41,19 @@ import org.zkoss.zul.Box;
import org.zkoss.zul.Vbox; import org.zkoss.zul.Vbox;
/** /**
* Dashboard item: Info views * Dashboard gadget: List of Info views
* @author Elaine * @author Elaine
* @date November 20, 2008 * @date November 20, 2008
*/ */
public class DPViews extends DashboardPanel implements EventListener<Event> { public class DPViews extends DashboardPanel implements EventListener<Event> {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = 8375414665766937581L; private static final long serialVersionUID = 8375414665766937581L;
/**
* Default constructor
*/
public DPViews() public DPViews()
{ {
super(); super();
@ -59,6 +61,10 @@ public class DPViews extends DashboardPanel implements EventListener<Event> {
this.appendChild(createViewPanel()); this.appendChild(createViewPanel());
} }
/**
* Layout panel
* @return {@link Box}
*/
private Box createViewPanel() private Box createViewPanel()
{ {
Vbox vbox = new Vbox(); Vbox vbox = new Vbox();
@ -163,6 +169,7 @@ public class DPViews extends DashboardPanel implements EventListener<Event> {
return vbox; return vbox;
} }
@Override
public void onEvent(Event event) public void onEvent(Event event)
{ {
Component comp = event.getTarget(); Component comp = event.getTarget();
@ -202,7 +209,7 @@ public class DPViews extends DashboardPanel implements EventListener<Event> {
} }
/** /**
* List of Info Windows to be displayed in the panel * Info Window to be displayed in the panel
* @author nmicoud * @author nmicoud
*/ */
private class ListInfoWindow { private class ListInfoWindow {
@ -210,15 +217,25 @@ public class DPViews extends DashboardPanel implements EventListener<Event> {
MInfoWindow iw = null; MInfoWindow iw = null;
int seqNo = 0; int seqNo = 0;
/**
* @param infoWindow
* @param seqNo
*/
public ListInfoWindow(MInfoWindow infoWindow, int seqNo) { public ListInfoWindow(MInfoWindow infoWindow, int seqNo) {
iw = infoWindow; iw = infoWindow;
this.seqNo = seqNo; this.seqNo = seqNo;
} }
/**
* @return Sequence Number
*/
public int getSeqNo() { public int getSeqNo() {
return seqNo; return seqNo;
} }
/**
* @return MInfoWindow
*/
public MInfoWindow getInfoWindow() { public MInfoWindow getInfoWindow() {
return iw; return iw;
} }

View File

@ -17,17 +17,20 @@ import org.adempiere.webui.component.Window;
import org.adempiere.webui.util.ServerPushTemplate; import org.adempiere.webui.util.ServerPushTemplate;
/** /**
* Custom dashboard item base class * Base class for dashboard gadget/widget
* @author Elaine * @author Elaine
* @date November 20, 2008 * @date November 20, 2008
*/ */
public abstract class DashboardPanel extends Window implements IDashboardPanel { public abstract class DashboardPanel extends Window implements IDashboardPanel {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = 7424244218250118823L; private static final long serialVersionUID = 7424244218250118823L;
/**
* Default constructor
*/
public DashboardPanel() public DashboardPanel()
{ {
super(); super();
@ -57,7 +60,7 @@ public abstract class DashboardPanel extends Window implements IDashboardPanel {
} }
/** /**
* Empty Dashboard Panels are not rendered on the Dashboard * Empty Dashboard Panel are not rendered on the Dashboard
* @return true if the panel is empty * @return true if the panel is empty
*/ */
public boolean isEmpty() { public boolean isEmpty() {

View File

@ -33,28 +33,30 @@ import org.zkoss.zk.ui.event.Events;
import org.zkoss.zk.ui.util.DesktopCleanup; import org.zkoss.zk.ui.util.DesktopCleanup;
/** /**
* * Runnable with weak reference to {@link Desktop} and a list of {@link DashboardPanel}.
* @author hengsin * @author hengsin
* @author Cristina Ghita, www.arhipac.ro BF [2871741] Error at start * @author Cristina Ghita, www.arhipac.ro BF [2871741] Error at start
* @see https://sourceforge.net/p/adempiere/zk-web-client/327/ * @see https://sourceforge.net/p/adempiere/zk-web-client/327/
*/ */
public class DashboardRunnable implements Runnable, Serializable public class DashboardRunnable implements Runnable, Serializable
{ {
/**
* generated serial id
*/
private static final long serialVersionUID = 5995227773511788894L; private static final long serialVersionUID = 5995227773511788894L;
private WeakReference<Desktop> desktop; private WeakReference<Desktop> desktop;
private List<DashboardPanel> dashboardPanels; private List<DashboardPanel> dashboardPanels;
private Locale locale; private Locale locale;
/** Desktop cleanup listener to call {@link #cleanup()} */
private DesktopCleanup listener; private DesktopCleanup listener;
@SuppressWarnings("unused") @SuppressWarnings("unused")
private static final CLogger logger = CLogger.getCLogger(DashboardRunnable.class); private static final CLogger logger = CLogger.getCLogger(DashboardRunnable.class);
/** /**
* * @param desktop zk Desktop instance
* @param desktop zk desktop interface
*/ */
public DashboardRunnable(Desktop desktop) { public DashboardRunnable(Desktop desktop) {
this.desktop = new WeakReference<Desktop>(desktop); this.desktop = new WeakReference<Desktop>(desktop);
@ -71,6 +73,9 @@ public class DashboardRunnable implements Runnable, Serializable
this.desktop.get().addListener(listener); this.desktop.get().addListener(listener);
} }
/**
* Perform clean up
*/
protected void cleanup() { protected void cleanup() {
dashboardPanels = null; dashboardPanels = null;
if (desktop != null && desktop.get() != null) if (desktop != null && desktop.get() != null)
@ -79,7 +84,8 @@ public class DashboardRunnable implements Runnable, Serializable
} }
/** /**
* @param tmp * Copy {@link #dashboardPanels} from tmp.
* @param tmp DashboardRunnable
* @param desktop * @param desktop
*/ */
public DashboardRunnable(DashboardRunnable tmp, Desktop desktop) { public DashboardRunnable(DashboardRunnable tmp, Desktop desktop) {
@ -88,6 +94,10 @@ public class DashboardRunnable implements Runnable, Serializable
tmp.cleanup(); tmp.cleanup();
} }
/**
* Refresh {@link #dashboardPanels} (usually call by background pooling thread).
* Delegate to {@link #refreshDashboard(boolean)}.
*/
@Override @Override
public void run() public void run()
{ {
@ -104,11 +114,11 @@ public class DashboardRunnable implements Runnable, Serializable
} }
/** /**
* Refresh dashboard content * Refresh {@link #dashboardPanels}
* @param pooling true if calling from pooling thread
*/ */
public void refreshDashboard(boolean pooling) public void refreshDashboard(boolean pooling)
{ {
ServerPushTemplate template = new ServerPushTemplate(desktop.get()); ServerPushTemplate template = new ServerPushTemplate(desktop.get());
//set thread local context if not in event thread //set thread local context if not in event thread
Properties ctx = null; Properties ctx = null;

View File

@ -39,14 +39,12 @@ import org.zkoss.zul.Center;
import org.zkoss.zul.South; import org.zkoss.zul.South;
/** /**
* * Window for Request Event
* @author Elaine * @author Elaine
*
*/ */
public class EventWindow extends Window implements EventListener<Event> { public class EventWindow extends Window implements EventListener<Event> {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = 4758066526040260586L; private static final long serialVersionUID = 4758066526040260586L;
private DatetimeBox dtBeginDate, dtEndDate; private DatetimeBox dtBeginDate, dtEndDate;
@ -55,6 +53,9 @@ public class EventWindow extends Window implements EventListener<Event> {
private int R_Request_ID = 0; private int R_Request_ID = 0;
/**
* Default constructor
*/
public EventWindow() { public EventWindow() {
super(); super();
@ -94,8 +95,7 @@ public class EventWindow extends Window implements EventListener<Event> {
confirmPanel = new ConfirmPanel(false, false, false, false, false, true); confirmPanel = new ConfirmPanel(false, false, false, false, false, true);
confirmPanel.addActionListener(this); confirmPanel.addActionListener(this);
Grid grid = GridFactory.newGridLayout(); Grid grid = GridFactory.newGridLayout();
Columns columns = new Columns(); Columns columns = new Columns();
@ -150,6 +150,10 @@ public class EventWindow extends Window implements EventListener<Event> {
south.appendChild(confirmPanel); south.appendChild(confirmPanel);
} }
/**
* Update UI component with details from event
* @param event {@link ADCalendarEvent}
*/
public void setData(ADCalendarEvent event) { public void setData(ADCalendarEvent event) {
txtHeaderColor.setStyle("background-color: " + event.getHeaderColor()); txtHeaderColor.setStyle("background-color: " + event.getHeaderColor());
txtContentColor.setStyle("background-color: " + event.getContentColor()); txtContentColor.setStyle("background-color: " + event.getContentColor());
@ -162,6 +166,7 @@ public class EventWindow extends Window implements EventListener<Event> {
confirmPanel.getButton(ConfirmPanel.A_ZOOM).setEnabled(R_Request_ID > 0); confirmPanel.getButton(ConfirmPanel.A_ZOOM).setEnabled(R_Request_ID > 0);
} }
@Override
public void onEvent(Event e) throws Exception { public void onEvent(Event e) throws Exception {
if (e.getTarget() == confirmPanel.getButton(ConfirmPanel.A_OK)) if (e.getTarget() == confirmPanel.getButton(ConfirmPanel.A_OK))
setVisible(false); setVisible(false);

View File

@ -45,34 +45,44 @@ import org.zkoss.zul.TreeNode;
import org.zkoss.zul.event.TreeDataEvent; import org.zkoss.zul.event.TreeDataEvent;
/** /**
* Favourite folder add or edit dialog * Favourite add or edit folder dialog
* *
* @author Logilite Technologies * @author Logilite Technologies
*/ */
public class FavouriteFolderDialog extends Window implements EventListener<Event> public class FavouriteFolderDialog extends Window implements EventListener<Event>
{ {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = -2838644830113603288L; private static final long serialVersionUID = -2838644830113603288L;
/** Folder name */
private Textbox txtFolder; private Textbox txtFolder;
/** For add mode, true to add to root instead of current selected parent folder node. */
private Checkbox chkAddAsRoot; private Checkbox chkAddAsRoot;
/** For IsCollapsible */
private Checkbox chkDefaultExpanded; private Checkbox chkDefaultExpanded;
private Label lblSelectedNodeInfo = new Label(); private Label lblSelectedNodeInfo = new Label();
private Borderlayout mainLayout = new Borderlayout(); private Borderlayout mainLayout = new Borderlayout();
/** Center of {@link #mainLayout} */
private Panel centerPanel = new Panel(); private Panel centerPanel = new Panel();
/** Grid layout of {@link #centerPanel} */
private Grid grid = new Grid(); private Grid grid = new Grid();
private ConfirmPanel confirmPanel = new ConfirmPanel(true); private ConfirmPanel confirmPanel = new ConfirmPanel(true);
/** Edit Mode: Node to edit. Add Mode: Parent folder node */
private MTreeFavoriteNode favNodeSummary; private MTreeFavoriteNode favNodeSummary;
private FavoriteSimpleTreeModel treeModel; private FavoriteSimpleTreeModel treeModel;
private Tree tree; private Tree tree;
/** True for add mode, false for edit mode */
private boolean isAdd; private boolean isAdd;
/**
* @param isAdd
* @param treeModel
* @param tree
*/
public FavouriteFolderDialog(boolean isAdd, FavoriteSimpleTreeModel treeModel, Tree tree) public FavouriteFolderDialog(boolean isAdd, FavoriteSimpleTreeModel treeModel, Tree tree)
{ {
super(); super();
@ -86,6 +96,9 @@ public class FavouriteFolderDialog extends Window implements EventListener<Event
initAttributes(); initAttributes();
} }
/**
* Layout dialog
*/
private void init() private void init()
{ {
if (isAdd) if (isAdd)
@ -245,6 +258,7 @@ public class FavouriteFolderDialog extends Window implements EventListener<Event
/** /**
* Insert Folder as Node to Tree. * Insert Folder as Node to Tree.
* @param folderName
*/ */
private void insertFolder(String folderName) private void insertFolder(String folderName)
{ {

View File

@ -17,7 +17,7 @@ import org.adempiere.webui.util.IServerPushCallback;
import org.adempiere.webui.util.ServerPushTemplate; import org.adempiere.webui.util.ServerPushTemplate;
/** /**
* Interface for dashboard panel * Interface for dashboard gadget/widget
* @author Elaine * @author Elaine
* @author hengsin * @author hengsin
* *
@ -25,8 +25,9 @@ import org.adempiere.webui.util.ServerPushTemplate;
public interface IDashboardPanel extends IServerPushCallback { public interface IDashboardPanel extends IServerPushCallback {
/** /**
* Refresh content of panel. For performance reason, keep the activate of desktop as short * Refresh content/model of panel. <br/>
* as possible. * To keep UI responsive, long running operation should be perform here outside of Event Listener Thread.<br/>
* Update of UI components should happens in the updateUI method (on Event Listener Thread) and should be completed in a short period of time.
* @param template * @param template
*/ */
public void refresh(ServerPushTemplate template); public void refresh(ServerPushTemplate template);

View File

@ -58,14 +58,14 @@ import org.zkoss.zul.Hlayout;
import org.zkoss.zul.South; import org.zkoss.zul.South;
/** /**
* Favorite node login to open menu and its sequence configuration dialog * Dialog to manage auto launch favourite items.
* *
* @author Logilite Technologies * @author Logilite Technologies
*/ */
public class LoginOpenSequenceDialog extends Window public class LoginOpenSequenceDialog extends Window
{ {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = -6200912526954948898L; private static final long serialVersionUID = -6200912526954948898L;
@ -79,7 +79,9 @@ public class LoginOpenSequenceDialog extends Window
private ConfirmPanel confirmPanel = new ConfirmPanel(true, false, true, false, false, false); private ConfirmPanel confirmPanel = new ConfirmPanel(true, false, true, false, false, false);
/** model for {@link #noList} */
private SimpleListModel noModel = new SimpleListModel(); private SimpleListModel noModel = new SimpleListModel();
/** model for {@link #yesList} */
private SimpleListModel yesModel = new SimpleListModel(); private SimpleListModel yesModel = new SimpleListModel();
private Listbox noList = new Listbox(); private Listbox noList = new Listbox();
@ -88,6 +90,7 @@ public class LoginOpenSequenceDialog extends Window
private Label noLabel = new Label(); private Label noLabel = new Label();
private Label yesLabel = new Label(); private Label yesLabel = new Label();
/** List for auto launch sequence */
private ArrayList<Integer> autoOpenSeqs = new ArrayList<Integer>(); private ArrayList<Integer> autoOpenSeqs = new ArrayList<Integer>();
private int m_AD_User_ID; private int m_AD_User_ID;
@ -371,7 +374,7 @@ public class LoginOpenSequenceDialog extends Window
/** /**
* @param event - Event * @param event - Event
*/ */
void migrateValueAcrossLists(Event event) protected void migrateValueAcrossLists(Event event)
{ {
Object source = event.getTarget(); Object source = event.getTarget();
if (source instanceof ListItem) if (source instanceof ListItem)
@ -393,7 +396,7 @@ public class LoginOpenSequenceDialog extends Window
* @param listTo * @param listTo
* @param endIndex * @param endIndex
*/ */
void migrateLists(Listbox listFrom, Listbox listTo, int endIndex) protected void migrateLists(Listbox listFrom, Listbox listTo, int endIndex)
{ {
int index = 0; int index = 0;
SimpleListModel lmFrom = (SimpleListModel) listFrom.getModel(); SimpleListModel lmFrom = (SimpleListModel) listFrom.getModel();
@ -425,7 +428,7 @@ public class LoginOpenSequenceDialog extends Window
* *
* @param event - Event * @param event - Event
*/ */
void migrateValueWithinYesList(int endIndex, List<ListElement> selObjects) protected void migrateValueWithinYesList(int endIndex, List<ListElement> selObjects)
{ {
int iniIndex = 0; int iniIndex = 0;
Arrays.sort(selObjects.toArray()); Arrays.sort(selObjects.toArray());
@ -445,7 +448,7 @@ public class LoginOpenSequenceDialog extends Window
* *
* @param event - Event * @param event - Event
*/ */
void migrateValueWithinYesList(Event event) protected void migrateValueWithinYesList(Event event)
{ {
Object[] selObjects = yesList.getSelectedItems().toArray(); Object[] selObjects = yesList.getSelectedItems().toArray();
@ -510,7 +513,7 @@ public class LoginOpenSequenceDialog extends Window
} // migrateValueWithinYesList } // migrateValueWithinYesList
/** /**
* Save Login open sequence no * Save auto launch configuration to DB
*/ */
public void saveData() public void saveData()
{ {
@ -560,7 +563,7 @@ public class LoginOpenSequenceDialog extends Window
private static class ListElement extends NamePair private static class ListElement extends NamePair
{ {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = -1717531470895073281L; private static final long serialVersionUID = -1717531470895073281L;
@ -621,13 +624,12 @@ public class LoginOpenSequenceDialog extends Window
} // ListElement } // ListElement
/** /**
* Drag Listener * Listener for onDrop event
*/ */
private class DragListener implements EventListener<Event> private class DragListener implements EventListener<Event>
{ {
/** /**
* Creates a ADSortTab.DragListener. * Default constructor
*/ */
public DragListener() public DragListener()
{ {

View File

@ -53,14 +53,12 @@ import org.zkoss.zul.Center;
import org.zkoss.zul.South; import org.zkoss.zul.South;
/** /**
* * Window for request
* @author Elaine * @author Elaine
*
*/ */
public class RequestWindow extends Window implements EventListener<Event> { public class RequestWindow extends Window implements EventListener<Event> {
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = 7757368164776005797L; private static final long serialVersionUID = 7757368164776005797L;
@ -79,6 +77,10 @@ public class RequestWindow extends Window implements EventListener<Event> {
private Window parent; private Window parent;
private Calendar calBegin,calEnd; private Calendar calBegin,calEnd;
/**
* @param ce CalendarsEvent
* @param parent
*/
public RequestWindow(CalendarsEvent ce, Window parent) { public RequestWindow(CalendarsEvent ce, Window parent) {
super(); super();
@ -279,6 +281,7 @@ public class RequestWindow extends Window implements EventListener<Event> {
tbxEndTime.setValue(ce.getEndDate()); tbxEndTime.setValue(ce.getEndDate());
} }
@Override
public void onEvent(Event e) throws Exception { public void onEvent(Event e) throws Exception {
if (m_readOnly) if (m_readOnly)
this.detach(); this.detach();
@ -322,7 +325,6 @@ public class RequestWindow extends Window implements EventListener<Event> {
{ {
if (log.isLoggable(Level.FINE)) log.fine("R_Request_ID=" + request.getR_Request_ID()); if (log.isLoggable(Level.FINE)) log.fine("R_Request_ID=" + request.getR_Request_ID());
Events.postEvent("onRefresh", parent, null); Events.postEvent("onRefresh", parent, null);
// Events.echoEvent("onRefresh", parent, null);
} }
else else
{ {
@ -336,7 +338,10 @@ public class RequestWindow extends Window implements EventListener<Event> {
this.detach(); this.detach();
} }
//Check, Start time is not >= End time, when Start Plan == Complete Plan /**
* Check, Start time is not >= End time, when Start Plan == Complete Plan
* @return true if {@link #calBegin} >= {@link #calEnd}, false otherwise (true indicate error)
*/
private boolean checkTime() private boolean checkTime()
{ {
calBegin = Calendar.getInstance(); calBegin = Calendar.getInstance();

View File

@ -36,9 +36,8 @@ import org.zkoss.zk.ui.event.EventListener;
import org.zkoss.zul.Window.Mode; import org.zkoss.zul.Window.Mode;
/** /**
* Base class for desktop implementation * Abstract base class for {@link IDesktop} implementation
* @author hengsin * @author hengsin
*
*/ */
public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop { public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop {
@ -50,11 +49,14 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
@SuppressWarnings("unused") @SuppressWarnings("unused")
private static final CLogger logger = CLogger.getCLogger(AbstractDesktop.class); private static final CLogger logger = CLogger.getCLogger(AbstractDesktop.class);
/**
* Default constructor
*/
public AbstractDesktop() { public AbstractDesktop() {
} }
/** /**
* Event listener for menu item selection. * Event listener for menu item selection.<br/>
* Identifies the action associated with the selected * Identifies the action associated with the selected
* menu item and acts accordingly. * menu item and acts accordingly.
* *
@ -63,6 +65,7 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
* @throws ApplicationException If the selected menu action has yet * @throws ApplicationException If the selected menu action has yet
* to be implemented * to be implemented
*/ */
@Override
public void onMenuSelected(int menuId) public void onMenuSelected(int menuId)
{ {
MMenu menu = MMenu.get(menuId); MMenu menu = MMenu.get(menuId);
@ -109,14 +112,13 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
} }
/** /**
* @return clientInfo * @return {@link ClientInfo}
*/ */
public ClientInfo getClientInfo() { public ClientInfo getClientInfo() {
return clientInfo; return clientInfo;
} }
/** /**
*
* @param clientInfo * @param clientInfo
*/ */
public void setClientInfo(ClientInfo clientInfo) { public void setClientInfo(ClientInfo clientInfo) {
@ -125,6 +127,7 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
/** /**
* @param win * @param win
* @param registered Window Number (start from 0)
*/ */
public int registerWindow(Object win) { public int registerWindow(Object win) {
List<Object> windows = getWindows(); List<Object> windows = getWindows();
@ -134,6 +137,7 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
} }
/** /**
* Remove from registered window list and clear environment context
* @param WindowNo * @param WindowNo
*/ */
public void unregisterWindow(int WindowNo) { public void unregisterWindow(int WindowNo) {
@ -144,7 +148,7 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
} }
/** /**
* * Find window by registered window number
* @param WindowNo * @param WindowNo
* @return Object * @return Object
*/ */
@ -158,24 +162,25 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
@Override @Override
public int findWindowNo(Component component) { public int findWindowNo(Component component) {
if (component == null) if (component == null)
return -1; return -1;
List<Object> windows = getWindows(); List<Object> windows = getWindows();
if (windows != null) { if (windows != null) {
if (windows.contains(component)) if (windows.contains(component))
return windows.indexOf(component); return windows.indexOf(component);
Component parent = component.getParent(); Component parent = component.getParent();
while (parent != null) { while (parent != null) {
if (windows.contains(parent)) if (windows.contains(parent))
return windows.indexOf(parent); return windows.indexOf(parent);
parent = parent.getParent(); parent = parent.getParent();
} }
} }
return -1; return -1;
} }
/** /**
* Delegate to {@link #showWindow(Window, String)}
* @param win * @param win
*/ */
public void showWindow(Window win) public void showWindow(Window win)
@ -185,10 +190,10 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
} }
/** /**
* when width of win set by stylesheet (css class or in style) win sometime don't in center. * When width of win set by stylesheet (css class or in style) win sometime don't position in center.<br/>
* fix by find out method change to {@link LayoutUtils#openOverlappedWindow(org.zkoss.zk.ui.Component, org.zkoss.zul.Window, String)} * To workaround that, use {@link LayoutUtils#openOverlappedWindow(org.zkoss.zk.ui.Component, org.zkoss.zul.Window, String)}.
* @param win * @param win Window
* @param pos * @param pos see {@link org.zkoss.zul.Window#setPosition(String)}
*/ */
public void showWindow(final Window win, final String pos) public void showWindow(final Window win, final String pos)
{ {
@ -218,6 +223,12 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
} }
} }
/**
*
* @param win Window
* @param pos see {@link org.zkoss.zul.Window#setPosition(String)}
* @param mode {@link Mode} (POPUP, OVERLAPPED, EMBEDDED or HIGHLIGHTED)
*/
private void showNonModalWindow(final Window win, final String pos, private void showNonModalWindow(final Window win, final String pos,
final Mode mode) { final Mode mode) {
if (Mode.POPUP == mode) if (Mode.POPUP == mode)
@ -238,10 +249,14 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
} }
} }
/**
* Show {@link Mode#EMBEDDED} window
* @param win
*/
protected abstract void showEmbedded(Window win); protected abstract void showEmbedded(Window win);
/** /**
* * Show modal window.
* @param win * @param win
*/ */
protected void showModal(final Window win) protected void showModal(final Window win)
@ -289,9 +304,9 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
} }
/** /**
* * Show {@link Mode#POPUP} window
* @param win * @param win Window
* @param position * @param position see {@link org.zkoss.zul.Window#setPosition(String)}
*/ */
protected void showPopup(Window win, String position) protected void showPopup(Window win, String position)
{ {
@ -306,9 +321,9 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
} }
/** /**
* * Show {@link Mode#OVERLAPPED} window
* @param win * @param win Window
* @param position * @param position see {@link org.zkoss.zul.Window#setPosition(String)}
*/ */
protected void showOverlapped(Window win, String position) protected void showOverlapped(Window win, String position)
{ {
@ -323,9 +338,9 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
} }
/** /**
* * Show {@link Mode#HIGHLIGHTED} window
* @param win * @param win Window
* @param position * @param position see {@link org.zkoss.zul.Window#setPosition(String)}
*/ */
protected void showHighlighted(Window win, String position) protected void showHighlighted(Window win, String position)
{ {
@ -339,6 +354,9 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
win.focus(); win.focus();
} }
/**
* @return List of registered windows
*/
protected List<Object> getWindows(){ protected List<Object> getWindows(){
Desktop desktop = getComponent().getDesktop(); Desktop desktop = getComponent().getDesktop();
if (desktop != null) { if (desktop != null) {
@ -355,18 +373,30 @@ public abstract class AbstractDesktop extends AbstractUIPart implements IDesktop
} }
} }
/**
* @param predefinedVariables
*/
public void setPredefinedContextVariables(String predefinedVariables) { public void setPredefinedContextVariables(String predefinedVariables) {
this.predefinedContextVariables = predefinedVariables; this.predefinedContextVariables = predefinedVariables;
} }
/**
* @return {@link #predefinedContextVariables}
*/
protected String getPredefinedContextVariables() { protected String getPredefinedContextVariables() {
return this.predefinedContextVariables; return this.predefinedContextVariables;
} }
/**
* @param isSOTrx
*/
public void setMenuIsSOTrx(boolean isSOTrx) { public void setMenuIsSOTrx(boolean isSOTrx) {
this.menuIsSOTrx = isSOTrx; this.menuIsSOTrx = isSOTrx;
} }
/**
* @return {@link #menuIsSOTrx}
*/
protected boolean isMenuSOTrx() { protected boolean isMenuSOTrx() {
return this.menuIsSOTrx; return this.menuIsSOTrx;
} }

View File

@ -124,8 +124,8 @@ import org.zkoss.zul.Toolbarbutton;
import org.zkoss.zul.Vlayout; import org.zkoss.zul.Vlayout;
/** /**
* Dashboard renderer and controller
* @author hengsin * @author hengsin
*
*/ */
public class DashboardController implements EventListener<Event> { public class DashboardController implements EventListener<Event> {
@ -134,14 +134,21 @@ public class DashboardController implements EventListener<Event> {
private Component prevParent; private Component prevParent;
private Component prevNext; private Component prevNext;
/** dashboard gadget panels */
private List<Panel> panelList = new ArrayList<Panel>(); private List<Panel> panelList = new ArrayList<Panel>();
/** For column orientation */
private List<Anchorchildren> columnList; private List<Anchorchildren> columnList;
/** For row orientation */
private List<Anchorchildren> rowList; private List<Anchorchildren> rowList;
private Anchorlayout dashboardLayout; private Anchorlayout dashboardLayout;
private Anchorchildren maximizedHolder; private Anchorchildren maximizedHolder;
/** Runnable for pooling refresh of dashboard gadgets */
private DashboardRunnable dashboardRunnable; private DashboardRunnable dashboardRunnable;
/** Timer for {@link #dashboardRunnable} */
private Timer dashboardTimer; private Timer dashboardTimer;
/** True for dashboard, false for left/right side panel */
private boolean isShowInDashboard; private boolean isShowInDashboard;
/** number of columns for column oriented dashboard */
private int noOfCols; private int noOfCols;
private static final String PANEL_EMPTY_ATTRIBUTE = "panel.empty"; private static final String PANEL_EMPTY_ATTRIBUTE = "panel.empty";
@ -153,10 +160,15 @@ public class DashboardController implements EventListener<Event> {
private static final String FLEX_GROW_ATTRIBUTE = "FlexGrow"; private static final String FLEX_GROW_ATTRIBUTE = "FlexGrow";
private static final String IMAGES_CONTEXT_HELP_PNG = "images/Help16.png"; private static final String IMAGES_CONTEXT_HELP_PNG = "images/Help16.png";
/** Default total width for column oriented layout (in percentage) */
private final static int DEFAULT_DASHBOARD_WIDTH = 99; private final static int DEFAULT_DASHBOARD_WIDTH = 99;
/** Column orientation */
private final static String DASHBOARD_LAYOUT_COLUMNS = "C"; private final static String DASHBOARD_LAYOUT_COLUMNS = "C";
/** Row orientation */
private final static String DASHBOARD_LAYOUT_ROWS = "R"; private final static String DASHBOARD_LAYOUT_ROWS = "R";
/** Max number of gadgets in a row. For row oriented layout. */
private final static int MAX_NO_OF_PREFS_IN_ROW = 10; private final static int MAX_NO_OF_PREFS_IN_ROW = 10;
/** Default horizontal flex grow for dashboard gadget. For row oriented layout. */
private final static int DEFAULT_FLEX_GROW = 1; private final static int DEFAULT_FLEX_GROW = 1;
/** /**
@ -174,10 +186,10 @@ public class DashboardController implements EventListener<Event> {
} }
/** /**
* * Render main or side dashboard
* @param parent * @param parent Parent Component of dashboard
* @param desktopImpl * @param desktopImpl IDesktop
* @param isShowInDashboard * @param isShowInDashboard true for main/center dashboard, false for left/right side dashboard
*/ */
public void render(Component parent, IDesktop desktopImpl, boolean isShowInDashboard) { public void render(Component parent, IDesktop desktopImpl, boolean isShowInDashboard) {
@ -188,6 +200,13 @@ public class DashboardController implements EventListener<Event> {
renderColumns(parent, desktopImpl, isShowInDashboard, false); renderColumns(parent, desktopImpl, isShowInDashboard, false);
} }
/**
* Render dashboard in column orientation
* @param parent Component
* @param desktopImpl IDesktop
* @param isShowInDashboard true for dashboard, false for left/right side panel
* @param update true for update, false for new
*/
protected void renderColumns(Component parent, IDesktop desktopImpl, boolean isShowInDashboard, boolean update) { protected void renderColumns(Component parent, IDesktop desktopImpl, boolean isShowInDashboard, boolean update) {
this.isShowInDashboard = isShowInDashboard; this.isShowInDashboard = isShowInDashboard;
if (!update) if (!update)
@ -371,6 +390,12 @@ public class DashboardController implements EventListener<Event> {
} }
} }
/**
* Create new gadget panel
* @param dp
* @param dc
* @return {@link Panel}
*/
private Panel newGadgetPanel(MDashboardPreference dp, MDashboardContent dc) { private Panel newGadgetPanel(MDashboardPreference dp, MDashboardContent dc) {
Panel panel; Panel panel;
panel = new Panel(); panel = new Panel();
@ -402,6 +427,11 @@ public class DashboardController implements EventListener<Event> {
return panel; return panel;
} }
/**
* Render help button for individual dashboard gadget
* @param caption
* @param text
*/
private void renderHelpButton(Caption caption, String text) { private void renderHelpButton(Caption caption, String text) {
A help = new A(); A help = new A();
help.setSclass("dashboard-content-help-icon"); help.setSclass("dashboard-content-help-icon");
@ -433,12 +463,12 @@ public class DashboardController implements EventListener<Event> {
/** /**
* Render gadget panel in background thread * Render gadget panel in background thread
* @param spt * @param spt ServerPushTemplate
* @param dashboardContent * @param dashboardContent MDashboardContent
* @param panel * @param panel Panel
* @param contextPath * @param contextPath
* @param panelChildren * @param panelChildren Panelchildren
* @param zulComponent * @param zulComponent Component created from zul in Event Listener thread
* @throws Exception * @throws Exception
*/ */
private void asyncRenderGadgetPanel(ServerPushTemplate spt, MDashboardContent dashboardContent, Panel panel, String contextPath, private void asyncRenderGadgetPanel(ServerPushTemplate spt, MDashboardContent dashboardContent, Panel panel, String contextPath,
@ -479,6 +509,10 @@ public class DashboardController implements EventListener<Event> {
} }
} }
/**
* Start {@link #dashboardRunnable} for pooling refresh of dashboard gadgets (using {@link #dashboardTimer})
* @param parent
*/
private void startDashboardRunnable(Component parent) { private void startDashboardRunnable(Component parent) {
// default Update every one minutes // default Update every one minutes
int interval = MSysConfig.getIntValue(MSysConfig.ZK_DASHBOARD_REFRESH_INTERVAL, 60000); int interval = MSysConfig.getIntValue(MSysConfig.ZK_DASHBOARD_REFRESH_INTERVAL, 60000);
@ -496,6 +530,13 @@ public class DashboardController implements EventListener<Event> {
dashboardTimer.setPage(parent.getPage()); dashboardTimer.setPage(parent.getPage());
} }
/**
* Render dashboard in row orientation
* @param parent
* @param desktopImpl
* @param isShowInDashboard
* @param update
*/
protected void renderRows(Component parent, IDesktop desktopImpl, boolean isShowInDashboard, boolean update) { protected void renderRows(Component parent, IDesktop desktopImpl, boolean isShowInDashboard, boolean update) {
this.isShowInDashboard = isShowInDashboard; this.isShowInDashboard = isShowInDashboard;
if (!update) if (!update)
@ -670,7 +711,6 @@ public class DashboardController implements EventListener<Event> {
{ {
logger.log(Level.WARNING, "Failed to create dashboard content", e); logger.log(Level.WARNING, "Failed to create dashboard content", e);
} }
//
if (!update) if (!update)
{ {
@ -678,6 +718,12 @@ public class DashboardController implements EventListener<Event> {
} }
} }
/**
* Find dashboard gadget panel by PA_DashboardContent_ID and PA_DashboardPreference_ID
* @param PA_DashboardContent_ID
* @param PA_DashboardPreference_ID
* @return {@link Panel}
*/
private Panel findPanel(int PA_DashboardContent_ID, int PA_DashboardPreference_ID) { private Panel findPanel(int PA_DashboardContent_ID, int PA_DashboardPreference_ID) {
for(Panel panel : panelList) { for(Panel panel : panelList) {
Object value1 = panel.getAttribute(MDashboardPreference.COLUMNNAME_PA_DashboardContent_ID); Object value1 = panel.getAttribute(MDashboardPreference.COLUMNNAME_PA_DashboardContent_ID);
@ -694,13 +740,13 @@ public class DashboardController implements EventListener<Event> {
/** /**
* Create gadget components in background thread * Create gadget components in background thread
* @param dashboardContent * @param dashboardContent MDashboardContent
* @param dashboardRunnable * @param dashboardRunnable DashboardRunnable
* @param contextPath * @param contextPath
* @param parentComponent * @param parentComponent
* @param components * @param components list to add created Component
* @param zulComponent * @param zulComponent Component created from zul in Event Listener thread
* @param spt * @param spt ServerPushTemplate
* @throws Exception * @throws Exception
*/ */
private void asyncRenderComponents(MDashboardContent dashboardContent, DashboardRunnable dashboardRunnable, String contextPath, private void asyncRenderComponents(MDashboardContent dashboardContent, DashboardRunnable dashboardRunnable, String contextPath,
@ -932,10 +978,10 @@ public class DashboardController implements EventListener<Event> {
} }
/** /**
* Synchronous render of gadget content in foreground ui thread * Synchronous render of gadget content in foreground UI (Event Listener) thread
* @param content must be an instanceof {@link HtmlBasedComponent} * @param content must be an instanceof {@link HtmlBasedComponent}
* @param dashboardContent * @param dashboardContent MDashboardContent
* @param dashboardRunnable * @param dashboardRunnable DashboardRunnable
* @return true if gadget dashboard is not empty * @return true if gadget dashboard is not empty
* @throws Exception * @throws Exception
*/ */
@ -974,8 +1020,9 @@ public class DashboardController implements EventListener<Event> {
} }
/** /**
* Add Drill Across Event Listener to Border Layout * Add onDrillAcross, onZoom and onDrillDown Event Listener to component
* @param processID * @param processID AD_Process_ID
* @param component Component
*/ */
private void addDrillAcrossEventListener(int processID, Component component) { private void addDrillAcrossEventListener(int processID, Component component) {
component.addEventListener(DrillEvent.ON_DRILL_ACROSS, new EventListener<Event>() { component.addEventListener(DrillEvent.ON_DRILL_ACROSS, new EventListener<Event>() {
@ -1021,7 +1068,7 @@ public class DashboardController implements EventListener<Event> {
/** /**
* Execute Drill to Query * Execute Drill to Query
* @param query query * @param query MQuery
*/ */
private void executeDrill (MQuery query) private void executeDrill (MQuery query)
{ {
@ -1212,6 +1259,11 @@ public class DashboardController implements EventListener<Event> {
return wrapper; return wrapper;
} }
/**
* Create and save dashboard preference (MDashboardPreference) to DB.
* @param AD_User_ID
* @param AD_Role_ID
*/
private void createDashboardPreference(int AD_User_ID, int AD_Role_ID) private void createDashboardPreference(int AD_User_ID, int AD_Role_ID)
{ {
MDashboardContent[] dcs = MDashboardContentAccess.get(Env.getCtx(),AD_Role_ID, AD_User_ID, null); MDashboardContent[] dcs = MDashboardContentAccess.get(Env.getCtx(),AD_Role_ID, AD_User_ID, null);
@ -1232,7 +1284,13 @@ public class DashboardController implements EventListener<Event> {
} }
} }
/**
* Update dashboard preference (MDashboardPreference) in DB.
* @param dps
* @param dcs
* @param ctx
* @return true if there are changes
*/
private boolean updatePreferences(MDashboardPreference[] dps,MDashboardContent[] dcs, Properties ctx) { private boolean updatePreferences(MDashboardPreference[] dps,MDashboardContent[] dcs, Properties ctx) {
boolean change = false; boolean change = false;
for (int i = 0; i < dcs.length; i++) { for (int i = 0; i < dcs.length; i++) {
@ -1273,6 +1331,11 @@ public class DashboardController implements EventListener<Event> {
return change; return change;
} }
/**
* Save dashboard preference (MDashboardPreference) to DB.
* @param layout
* @param prevLayout
*/
private void saveDashboardPreference(Component layout, Component prevLayout) private void saveDashboardPreference(Component layout, Component prevLayout)
{ {
String layoutOrientation = MSysConfig.getValue(MSysConfig.DASHBOARD_LAYOUT_ORIENTATION, Env.getAD_Client_ID(Env.getCtx())); String layoutOrientation = MSysConfig.getValue(MSysConfig.DASHBOARD_LAYOUT_ORIENTATION, Env.getAD_Client_ID(Env.getCtx()));
@ -1456,7 +1519,6 @@ public class DashboardController implements EventListener<Event> {
} }
/** /**
*
* @param page * @param page
* @param desktop * @param desktop
*/ */
@ -1484,12 +1546,22 @@ public class DashboardController implements EventListener<Event> {
dashboardLayout = null; dashboardLayout = null;
} }
/**
* add dashboardPanel to {@link #dashboardRunnable}
* @param dashboardPanel
*/
private void addDashboardPanel(DashboardPanel dashboardPanel) { private void addDashboardPanel(DashboardPanel dashboardPanel) {
if (dashboardRunnable != null) { if (dashboardRunnable != null) {
dashboardRunnable.add(dashboardPanel); dashboardRunnable.add(dashboardPanel);
} }
} }
/**
* Strip &lt;html&gt;, &lt;body&gt; and &lt;head&gt; tag
* @param htmlString
* @param all true to escpae &lt; and &gt;
* @return stripped htmlString
*/
private String stripHtml(String htmlString, boolean all) { private String stripHtml(String htmlString, boolean all) {
htmlString = htmlString htmlString = htmlString
.replace("<html>", "") .replace("<html>", "")
@ -1506,6 +1578,13 @@ public class DashboardController implements EventListener<Event> {
return htmlString; return htmlString;
} }
/**
* Run report
* @param AD_Process_ID
* @param AD_PrintFormat_ID
* @param parameters Report parameters
* @return {@link ReportEngine}
*/
private ReportEngine runReport(int AD_Process_ID, int AD_PrintFormat_ID, String parameters) { private ReportEngine runReport(int AD_Process_ID, int AD_PrintFormat_ID, String parameters) {
MProcess process = MProcess.get(Env.getCtx(), AD_Process_ID); MProcess process = MProcess.get(Env.getCtx(), AD_Process_ID);
if (!process.isReport() || process.getAD_ReportView_ID() == 0) if (!process.isReport() || process.getAD_ReportView_ID() == 0)
@ -1546,6 +1625,16 @@ public class DashboardController implements EventListener<Event> {
} }
/**
* Generate report media (html)
* @param AD_Process_ID
* @param AD_PrintFormat_ID
* @param parameters
* @param component
* @param contextPath
* @return {@link AMedia}
* @throws Exception
*/
private AMedia generateReport(int AD_Process_ID, int AD_PrintFormat_ID, String parameters, Component component, String contextPath) throws Exception { private AMedia generateReport(int AD_Process_ID, int AD_PrintFormat_ID, String parameters, Component component, String contextPath) throws Exception {
ReportEngine re = runReport(AD_Process_ID, AD_PrintFormat_ID, parameters); ReportEngine re = runReport(AD_Process_ID, AD_PrintFormat_ID, parameters);
if(re == null) if(re == null)
@ -1556,6 +1645,12 @@ public class DashboardController implements EventListener<Event> {
return new AMedia(re.getName(), "html", "text/html", file, false); return new AMedia(re.getName(), "html", "text/html", file, false);
} }
/**
* Run report and open in report viewer
* @param AD_Process_ID
* @param AD_PrintFormat_ID
* @param parameters
*/
protected void openReportInViewer(int AD_Process_ID, int AD_PrintFormat_ID, String parameters) { protected void openReportInViewer(int AD_Process_ID, int AD_PrintFormat_ID, String parameters) {
ReportEngine re = runReport(AD_Process_ID, AD_PrintFormat_ID, parameters); ReportEngine re = runReport(AD_Process_ID, AD_PrintFormat_ID, parameters);
new ZkReportViewerProvider().openViewer(re); new ZkReportViewerProvider().openViewer(re);
@ -1747,10 +1842,8 @@ public class DashboardController implements EventListener<Event> {
MProcessPara pp = MProcess.get(i.getAD_Process_ID()).getParameter(ip.getParameterName()); MProcessPara pp = MProcess.get(i.getAD_Process_ID()).getParameter(ip.getParameterName());
if (pp != null) { if (pp != null) {
MLookupInfo mli = MLookupFactory.getLookupInfo(Env.getCtx(), 0, 0, pp.getAD_Reference_ID(), Env.getLanguage(Env.getCtx()), pp.getColumnName(), pp.getAD_Reference_Value_ID(), false, ""); MLookupInfo mli = MLookupFactory.getLookupInfo(Env.getCtx(), 0, 0, pp.getAD_Reference_ID(), Env.getLanguage(Env.getCtx()), pp.getColumnName(), pp.getAD_Reference_Value_ID(), false, "");
PreparedStatement pstmt = null; PreparedStatement pstmt = null;
ResultSet rs = null; ResultSet rs = null;
StringBuilder name = new StringBuilder(""); StringBuilder name = new StringBuilder("");
@ -1793,7 +1886,6 @@ public class DashboardController implements EventListener<Event> {
} }
/** /**
*
* @param clientInfo * @param clientInfo
*/ */
public void updateLayout(ClientInfo clientInfo) { public void updateLayout(ClientInfo clientInfo) {
@ -1819,6 +1911,14 @@ public class DashboardController implements EventListener<Event> {
} }
} }
/**
* Render chart
* @param chartPanel
* @param width
* @param height
* @param model {@link ChartModel}
* @param showTitle
*/
private void renderChart(final Div chartPanel, int width, int height, ChartModel model, boolean showTitle) { private void renderChart(final Div chartPanel, int width, int height, ChartModel model, boolean showTitle) {
List<IChartRendererService> list = Extensions.getChartRendererServices(); List<IChartRendererService> list = Extensions.getChartRendererServices();
for (IChartRendererService renderer : list) { for (IChartRendererService renderer : list) {

View File

@ -101,7 +101,7 @@ import org.zkoss.zul.West;
/** /**
* *
* Default desktop implementation. * Default {@link IDesktop} implementation.
* @author <a href="mailto:agramdass@gmail.com">Ashley G Ramdass</a> * @author <a href="mailto:agramdass@gmail.com">Ashley G Ramdass</a>
* @author <a href="mailto:hengsin@gmail.com">Low Heng Sin</a> * @author <a href="mailto:hengsin@gmail.com">Low Heng Sin</a>
* @date Mar 2, 2007 * @date Mar 2, 2007
@ -109,13 +109,9 @@ import org.zkoss.zul.West;
* @author Deepak Pansheriya/Vivek - Adding support for message broadcasting * @author Deepak Pansheriya/Vivek - Adding support for message broadcasting
*/ */
public class DefaultDesktop extends TabbedDesktop implements MenuListener, Serializable, EventListener<Event>, EventHandler, DesktopCleanup public class DefaultDesktop extends TabbedDesktop implements MenuListener, Serializable, EventListener<Event>, EventHandler, DesktopCleanup
{ {
private static final String POPUP_OPEN_ATTR = "popup.open";
private static final String HOME_TAB_RENDER_ATTR = "homeTab.render";
/** /**
* * generated serial id
*/ */
private static final long serialVersionUID = 7189914859100400758L; private static final long serialVersionUID = 7189914859100400758L;
@ -127,49 +123,73 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
private static final String IMAGES_THREELINE_MENU_PNG = "images/threelines.png"; private static final String IMAGES_THREELINE_MENU_PNG = "images/threelines.png";
private static final String POPUP_OPEN_ATTR = "popup.open";
private static final String HOME_TAB_RENDER_ATTR = "homeTab.render";
private static final String HELP_CONTROLLER_WIDTH_PREFERENCE = "HelpController.Width";
private static final String SIDE_CONTROLLER_WIDTH_PREFERENCE = "SideController.Width";
@SuppressWarnings("unused") @SuppressWarnings("unused")
private static final CLogger logger = CLogger.getCLogger(DefaultDesktop.class); private static final CLogger logger = CLogger.getCLogger(DefaultDesktop.class);
/** Main layout. With id "layout" in desktop.zul */
private Borderlayout layout; private Borderlayout layout;
private int noCount; private int noCount;
/** Panel of home tab */
private Tabpanel homeTab; private Tabpanel homeTab;
private DashboardController dashboardController, sideController; private DashboardController dashboardController, sideController;
/** HeaderPanel of {@link #headerContainer}. With id "header" in desktop.zul */
private HeaderPanel pnlHead; private HeaderPanel pnlHead;
private Desktop m_desktop = null; private Desktop m_desktop = null;
/** Renderer and controller for help and quick info panel */
private HelpController helpController; private HelpController helpController;
/** Button to hide or show North desktop header. Visible for mobile client. */
private ToolBarButton max; private ToolBarButton max;
/** Button to hide or show help and quick info panels */
private ToolBarButton contextHelp; private ToolBarButton contextHelp;
/** Button to open north header popup. Visible when {@link #max} is true. */
private ToolBarButton showHeader; private ToolBarButton showHeader;
/** Body component of north header. With id "northBody" in desktop.zul */
private Component headerContainer; private Component headerContainer;
/** Popup open by {@link #showHeader} */
private Window headerPopup; private Window headerPopup;
private Image logo; private Image logo;
/** true if client browser is a mobile browser */
private boolean mobile; private boolean mobile;
/** Help and quick info popup for mobile client */
private Popup eastPopup; private Popup eastPopup;
/** West panel popup for mobile client */
private Popup westPopup; private Popup westPopup;
/** Button to show {@link #westPopup}. Visible for mobile client. */
private ToolBarButton westBtn; private ToolBarButton westBtn;
// For quick info optimization // For quick info optimization
private GridTab gridTab; private GridTab gridTab;
// Right side Quick info is visible /** True if Right side Quick info is visible */
private boolean isQuickInfoOpen = true; private boolean isQuickInfoOpen = true;
/**
* Default constructor
*/
public DefaultDesktop() public DefaultDesktop()
{ {
super(); super();
@ -191,6 +211,9 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
queue.subscribe(this); queue.subscribe(this);
} }
/**
* Create desktop layout from "zul/desktop/desktop.zul".
*/
@SuppressWarnings("serial") @SuppressWarnings("serial")
protected Component doCreatePart(Component parent) protected Component doCreatePart(Component parent)
{ {
@ -446,9 +469,11 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
return layout; return layout;
} }
private String getWestWidthPreference() { /**
* @return saved width for west panel. null if there's no saved width.
String width = Env.getPreference(Env.getCtx(), 0, "SideController.Width", false); */
private String getWestWidthPreference() {
String width = Env.getPreference(Env.getCtx(), 0, SIDE_CONTROLLER_WIDTH_PREFERENCE, false);
if( (! Util.isEmpty(width)) ){ if( (! Util.isEmpty(width)) ){
ClientInfo browserInfo = getClientInfo(); ClientInfo browserInfo = getClientInfo();
@ -462,8 +487,11 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
return null; return null;
} }
/**
* Save width of west panel as user preference
* @param width
*/
protected void updateSideControllerWidthPreference(String width) { protected void updateSideControllerWidthPreference(String width) {
if( width != null ){ if( width != null ){
Query query = new Query(Env.getCtx(), Query query = new Query(Env.getCtx(),
MTable.get(Env.getCtx(), I_AD_Preference.Table_ID), MTable.get(Env.getCtx(), I_AD_Preference.Table_ID),
@ -474,14 +502,13 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
MPreference preference = query.setOnlyActiveRecords(true) MPreference preference = query.setOnlyActiveRecords(true)
.setApplyAccessFilter(true) .setApplyAccessFilter(true)
.setClient_ID() .setClient_ID()
.setParameters("SideController.Width", userId) .setParameters(SIDE_CONTROLLER_WIDTH_PREFERENCE, userId)
.first(); .first();
if ( preference == null || preference.getAD_Preference_ID() <= 0 ) { if ( preference == null || preference.getAD_Preference_ID() <= 0 ) {
preference = new MPreference(Env.getCtx(), 0, null); preference = new MPreference(Env.getCtx(), 0, null);
preference.setAD_User_ID(userId); // allow System preference.setAD_User_ID(userId); // allow System
preference.setAttribute("SideController.Width"); preference.setAttribute(SIDE_CONTROLLER_WIDTH_PREFERENCE);
} }
preference.setValue(width); preference.setValue(width);
preference.saveEx(); preference.saveEx();
@ -490,9 +517,11 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
} }
private String getEastWidthPreference() { /**
* @return saved width of east/help panel. null if there's no saved width.
String width = Env.getPreference(Env.getCtx(), 0, "HelpController.Width", false); */
private String getEastWidthPreference() {
String width = Env.getPreference(Env.getCtx(), 0, HELP_CONTROLLER_WIDTH_PREFERENCE, false);
if( (! Util.isEmpty(width)) ){ if( (! Util.isEmpty(width)) ){
ClientInfo browserInfo = getClientInfo(); ClientInfo browserInfo = getClientInfo();
@ -506,8 +535,11 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
return null; return null;
} }
protected void updateHelpWidthPreference(String width) { /**
* Save width of east/help panel as user preference
* @param width
*/
protected void updateHelpWidthPreference(String width) {
if( width != null ){ if( width != null ){
Query query = new Query(Env.getCtx(), Query query = new Query(Env.getCtx(),
MTable.get(Env.getCtx(), I_AD_Preference.Table_ID), MTable.get(Env.getCtx(), I_AD_Preference.Table_ID),
@ -518,14 +550,13 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
MPreference preference = query.setOnlyActiveRecords(true) MPreference preference = query.setOnlyActiveRecords(true)
.setApplyAccessFilter(true) .setApplyAccessFilter(true)
.setClient_ID() .setClient_ID()
.setParameters("HelpController.Width", userId) .setParameters(HELP_CONTROLLER_WIDTH_PREFERENCE, userId)
.first(); .first();
if ( preference == null || preference.getAD_Preference_ID() <= 0 ) { if ( preference == null || preference.getAD_Preference_ID() <= 0 ) {
preference = new MPreference(Env.getCtx(), 0, null); preference = new MPreference(Env.getCtx(), 0, null);
preference.setAD_User_ID(userId); // allow System preference.setAD_User_ID(userId); // allow System
preference.setAttribute("HelpController.Width"); preference.setAttribute(HELP_CONTROLLER_WIDTH_PREFERENCE);
} }
preference.setValue(width); preference.setValue(width);
preference.saveEx(); preference.saveEx();
@ -533,24 +564,40 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
} }
/**
* Save west/menu panel collapsed state as user preference
* @param collapsed
*/
private void updateMenuCollapsedPreference(boolean collapsed) { private void updateMenuCollapsedPreference(boolean collapsed) {
UserPreference pref = SessionManager.getSessionApplication().getUserPreference(); UserPreference pref = SessionManager.getSessionApplication().getUserPreference();
pref.setProperty(UserPreference.P_MENU_COLLAPSED, collapsed); pref.setProperty(UserPreference.P_MENU_COLLAPSED, collapsed);
pref.savePreference(); pref.savePreference();
} }
/**
* Save east/help panel collapsed state as user preference
* @param collapsed
*/
private void updateHelpCollapsedPreference(boolean collapsed) { private void updateHelpCollapsedPreference(boolean collapsed) {
UserPreference pref = SessionManager.getSessionApplication().getUserPreference(); UserPreference pref = SessionManager.getSessionApplication().getUserPreference();
pref.setProperty(UserPreference.P_HELP_COLLAPSED, collapsed); pref.setProperty(UserPreference.P_HELP_COLLAPSED, collapsed);
pref.savePreference(); pref.savePreference();
} }
/**
* Save page/desktop header collapsed state as user preference
* @param collapsed
*/
private void updateHeaderCollapsedPreference(boolean collapsed) { private void updateHeaderCollapsedPreference(boolean collapsed) {
UserPreference pref = SessionManager.getSessionApplication().getUserPreference(); UserPreference pref = SessionManager.getSessionApplication().getUserPreference();
pref.setProperty(UserPreference.P_HEADER_COLLAPSED, collapsed); pref.setProperty(UserPreference.P_HEADER_COLLAPSED, collapsed);
pref.savePreference(); pref.savePreference();
} }
/**
* Render content of home tab.<br/>
* Delegate to {@link DashboardController#render(Component, IDesktop, boolean)}
*/
public void renderHomeTab() public void renderHomeTab()
{ {
homeTab.getChildren().clear(); homeTab.getChildren().clear();
@ -609,6 +656,10 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
homeTab.invalidate(); homeTab.invalidate();
} }
/**
* Set width of popup for side panel
* @param popup
*/
protected void setSidePopupWidth(Popup popup) { protected void setSidePopupWidth(Popup popup) {
if (ClientInfo.minWidth(ClientInfo.LARGE_WIDTH)) if (ClientInfo.minWidth(ClientInfo.LARGE_WIDTH))
popup.setWidth("30%"); popup.setWidth("30%");
@ -624,6 +675,7 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
popup.setWidth("80%"); popup.setWidth("80%");
} }
@Override
public void onEvent(Event event) public void onEvent(Event event)
{ {
Component comp = event.getTarget(); Component comp = event.getTarget();
@ -697,6 +749,9 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
} }
} }
/**
* Make page/desktop header visible again
*/
protected void restoreHeader() { protected void restoreHeader() {
layout.getNorth().setVisible(true); layout.getNorth().setVisible(true);
if (ThemeManager.isUseFontIconForImage()) if (ThemeManager.isUseFontIconForImage())
@ -710,6 +765,9 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
updateHeaderCollapsedPreference(false); updateHeaderCollapsedPreference(false);
} }
/**
* Hide page/desktop header
*/
protected void collapseHeader() { protected void collapseHeader() {
layout.getNorth().setVisible(false); layout.getNorth().setVisible(false);
if (ThemeManager.isUseFontIconForImage()) if (ThemeManager.isUseFontIconForImage())
@ -739,7 +797,6 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
} }
/** /**
*
* @param page * @param page
*/ */
public void setPage(Page page) { public void setPage(Page page) {
@ -789,6 +846,11 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
} }
} }
/**
* Asynchronous logout. Call by {@link #logout(Callback)}.<br/>
* This is to workaround client side detached element leak.
* @param callback
*/
private void asyncLogout(Callback<Boolean> callback) { private void asyncLogout(Callback<Boolean> callback) {
unbindEventManager(); unbindEventManager();
if (dashboardController != null) { if (dashboardController != null) {
@ -816,14 +878,22 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
m_desktop = null; m_desktop = null;
} }
/**
* Update home tab title after {@link #ON_ACTIVITIES_CHANGED_EVENT}
*/
public void updateUI() { public void updateUI() {
windowContainer.setTabTitle(0, Util.cleanAmp(Msg.getMsg(Env.getCtx(), "Home")) + " (" + noCount + ")", null); windowContainer.setTabTitle(0, Util.cleanAmp(Msg.getMsg(Env.getCtx(), "Home")) + " (" + noCount + ")", null);
} }
//use _docClick undocumented api. need verification after major zk release update /**
* use _docClick undocumented api. need verification after major zk release update
*/
private final static String autoHideMenuScript = "(function(){try{let w=zk.Widget.$('#{0}');let t=zk.Widget.$('#{1}');" + private final static String autoHideMenuScript = "(function(){try{let w=zk.Widget.$('#{0}');let t=zk.Widget.$('#{1}');" +
"let e=new Object;e.target=t;w._docClick(e);}catch(error){}})()"; "let e=new Object;e.target=t;w._docClick(e);}catch(error){}})()";
/**
* Auto hide west panel or popup
*/
private void autoHideMenu() { private void autoHideMenu() {
if (mobile) { if (mobile) {
if (westPopup.getAttribute(POPUP_OPEN_ATTR) != null) { if (westPopup.getAttribute(POPUP_OPEN_ATTR) != null) {
@ -852,19 +922,23 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
autoHideMenu(); autoHideMenu();
} }
//Implementation for Broadcast message
/** /**
* Implementation for Broadcast message
*/ */
public void bindEventManager() { public void bindEventManager() {
EventManager.getInstance().register(IEventTopics.BROADCAST_MESSAGE, this); EventManager.getInstance().register(IEventTopics.BROADCAST_MESSAGE, this);
} }
/** /**
* Clean up for Broadcast message
*/ */
public void unbindEventManager() { public void unbindEventManager() {
EventManager.getInstance().unregister(this); EventManager.getInstance().unregister(this);
} }
/**
* Handle OSGi event for Broadcast message
*/
@Override @Override
public void handleEvent(final org.osgi.service.event.Event event) { public void handleEvent(final org.osgi.service.event.Event event) {
String eventName = event.getTopic(); String eventName = event.getTopic();
@ -1029,7 +1103,10 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
} }
} }
int getMenuID() /**
* @return Menu tree ID for login role
*/
protected int getMenuID()
{ {
int AD_Role_ID = Env.getAD_Role_ID(Env.getCtx()); int AD_Role_ID = Env.getAD_Role_ID(Env.getCtx());
int AD_Tree_ID = DB.getSQLValue(null, int AD_Tree_ID = DB.getSQLValue(null,
@ -1042,6 +1119,11 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
return AD_Tree_ID; return AD_Tree_ID;
} }
/**
* Process auto launch configuration after login (store in AD_Tree_Favorite_Node)
* @param ctx
*/
private void automaticOpen(Properties ctx) { private void automaticOpen(Properties ctx) {
if (isActionURL()) // IDEMPIERE-2334 vs IDEMPIERE-3000 - do not open windows when coming from an action URL if (isActionURL()) // IDEMPIERE-2334 vs IDEMPIERE-3000 - do not open windows when coming from an action URL
return; return;
@ -1107,6 +1189,9 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
} }
} }
/**
* Update width of side panel
*/
private void updateSideLayout() { private void updateSideLayout() {
if (westPopup != null && westPopup.getChildren().size() > 1) if (westPopup != null && westPopup.getChildren().size() > 1)
setSidePopupWidth(westPopup); setSidePopupWidth(westPopup);
@ -1114,6 +1199,9 @@ public class DefaultDesktop extends TabbedDesktop implements MenuListener, Seria
setSidePopupWidth(eastPopup); setSidePopupWidth(eastPopup);
} }
/**
* @return true if there's Action parameter in URL
*/
private boolean isActionURL() { private boolean isActionURL() {
ConcurrentMap<String, String[]> parameters = new ConcurrentHashMap<String, String[]>(Executions.getCurrent().getParameterMap()); ConcurrentMap<String, String[]> parameters = new ConcurrentHashMap<String, String[]>(Executions.getCurrent().getParameterMap());
String action = ""; String action = "";

View File

@ -33,8 +33,9 @@ import org.zkoss.zul.Tree;
*/ */
public class FavouriteController public class FavouriteController
{ {
/** Session attribute to store FavouriteController reference */
private static final String DESKTOP_FAVOURITE_CONTROLLER = "desktop.FavouriteController"; private static final String DESKTOP_FAVOURITE_CONTROLLER = "desktop.FavouriteController";
/** Node_ID:MTreeNode */
private Map<Integer, MTreeNode> nodeMap; private Map<Integer, MTreeNode> nodeMap;
private int m_AD_Tree_Favorite_ID; private int m_AD_Tree_Favorite_ID;
@ -45,11 +46,18 @@ public class FavouriteController
private Tree tree; private Tree tree;
private FavoriteSimpleTreeModel treeModel; private FavoriteSimpleTreeModel treeModel;
/**
* Private constructor.<br/>
* Use {@link #getInstance(Session)} to get singleton instance for a Session.
*/
private FavouriteController() private FavouriteController()
{ {
init(); init();
} }
/**
* Load user favourites
*/
private void init() private void init()
{ {
nodeMap = new LinkedHashMap<>(); nodeMap = new LinkedHashMap<>();
@ -102,7 +110,7 @@ public class FavouriteController
* Get favourites controller instance for current session * Get favourites controller instance for current session
* *
* @param currSess * @param currSess
* @return FavouriteController session instance * @return FavouriteController session instance
*/ */
public static synchronized FavouriteController getInstance(Session currSess) public static synchronized FavouriteController getInstance(Session currSess)
{ {
@ -116,6 +124,12 @@ public class FavouriteController
return controller; return controller;
} // getInstance } // getInstance
/**
*
* @param add true for add, false for delete
* @param Menu_ID
* @return true if add/delete is successful
*/
private boolean barUpdate(boolean add, int Menu_ID) private boolean barUpdate(boolean add, int Menu_ID)
{ {
if (add) if (add)
@ -144,7 +158,7 @@ public class FavouriteController
* Add node (by node id) to favourties * Add node (by node id) to favourties
* *
* @param nodeId * @param nodeId
* @return true if successfully added * @return true if successfully added
*/ */
public boolean addNode(int nodeId) public boolean addNode(int nodeId)
{ {
@ -160,7 +174,7 @@ public class FavouriteController
* add tree node to favourites * add tree node to favourites
* *
* @param node * @param node
* @return true if successfully added * @return true if successfully added
*/ */
public boolean addNode(MTreeNode node) public boolean addNode(MTreeNode node)
{ {
@ -188,7 +202,7 @@ public class FavouriteController
* remove node (by node id) from favourites * remove node (by node id) from favourites
* *
* @param nodeId * @param nodeId
* @return true if found and remove * @return true if found and remove
*/ */
public boolean removeNode(int nodeId) public boolean removeNode(int nodeId)
{ {
@ -213,7 +227,7 @@ public class FavouriteController
/** /**
* @param nodeId * @param nodeId
* @return true if node id is in the current favourites list * @return true if node id is in the current favourites list
*/ */
public boolean hasNode(int nodeId) public boolean hasNode(int nodeId)
{ {
@ -253,16 +267,26 @@ public class FavouriteController
deletedCallbacks.add(callback); deletedCallbacks.add(callback);
} }
/**
* @return AD_Tree_Favorite_ID
*/
public int getAD_Tree_Favorite_ID() public int getAD_Tree_Favorite_ID()
{ {
return m_AD_Tree_Favorite_ID; return m_AD_Tree_Favorite_ID;
} }
/**
* @return root MTreeNode
*/
public MTreeNode getRootNode() public MTreeNode getRootNode()
{ {
return rootNode; return rootNode;
} }
/**
* @param treeModel FavoriteSimpleTreeModel
* @param tree Tree
*/
public void setTreeAndModel(FavoriteSimpleTreeModel treeModel, Tree tree) public void setTreeAndModel(FavoriteSimpleTreeModel treeModel, Tree tree)
{ {
this.tree = tree; this.tree = tree;

View File

@ -25,6 +25,7 @@ import org.compiere.model.GridTab;
import org.compiere.model.MQuery; import org.compiere.model.MQuery;
import org.zkoss.zk.ui.Component; import org.zkoss.zk.ui.Component;
import org.zkoss.zk.ui.Page; import org.zkoss.zk.ui.Page;
import org.zkoss.zk.ui.event.EventQueue;
/** /**
* Desktop interface * Desktop interface
@ -34,6 +35,7 @@ import org.zkoss.zk.ui.Page;
public interface IDesktop extends UIPart { public interface IDesktop extends UIPart {
public static final String WINDOWNO_ATTRIBUTE = "desktop.windowno"; public static final String WINDOWNO_ATTRIBUTE = "desktop.windowno";
/** {@link EventQueue} name for activities (workflow activities, request, notice and unprocessed documents) */
public static final String ACTIVITIES_EVENT_QUEUE = "ActivitiesEventQueue"; public static final String ACTIVITIES_EVENT_QUEUE = "ActivitiesEventQueue";
public static final String ON_ACTIVITIES_CHANGED_EVENT = "onActivitiesChanged"; public static final String ON_ACTIVITIES_CHANGED_EVENT = "onActivitiesChanged";

View File

@ -48,21 +48,22 @@ import org.zkoss.zul.Tab;
import org.zkoss.zul.Tabpanels; import org.zkoss.zul.Tabpanels;
/** /**
* A Tabbed MDI implementation * Abstract base class for Tabbed MDI implementation
* @author hengsin * @author hengsin
*
*/ */
public abstract class TabbedDesktop extends AbstractDesktop { public abstract class TabbedDesktop extends AbstractDesktop {
/** Controller for open desktop windows. */
protected WindowContainer windowContainer; protected WindowContainer windowContainer;
/**
* Default constructor
*/
public TabbedDesktop() { public TabbedDesktop() {
super(); super();
windowContainer = new WindowContainer(); windowContainer = new WindowContainer();
} }
/** /**
*
* @param processId * @param processId
* @param soTrx * @param soTrx
* @return ProcessDialog * @return ProcessDialog
@ -83,9 +84,8 @@ public abstract class TabbedDesktop extends AbstractDesktop {
} }
/** /**
*
* @param formId * @param formId
* @return ADWindow * @return ADForm
*/ */
public ADForm openForm(int formId) { public ADForm openForm(int formId) {
ADForm form = ADForm.openForm(formId, null, null, getPredefinedContextVariables(), isMenuSOTrx()); ADForm form = ADForm.openForm(formId, null, null, getPredefinedContextVariables(), isMenuSOTrx());
@ -107,7 +107,6 @@ public abstract class TabbedDesktop extends AbstractDesktop {
} }
/** /**
*
* @param infoId * @param infoId
*/ */
@Override @Override
@ -128,7 +127,6 @@ public abstract class TabbedDesktop extends AbstractDesktop {
} }
/** /**
*
* @param workflow_ID * @param workflow_ID
*/ */
public void openWorkflow(int workflow_ID) { public void openWorkflow(int workflow_ID) {
@ -142,7 +140,6 @@ public abstract class TabbedDesktop extends AbstractDesktop {
} }
/** /**
*
* @param windowId * @param windowId
* @param callback * @param callback
*/ */
@ -151,7 +148,6 @@ public abstract class TabbedDesktop extends AbstractDesktop {
} }
/** /**
*
* @param windowId * @param windowId
* @param query * @param query
* @param callback * @param callback
@ -173,7 +169,6 @@ public abstract class TabbedDesktop extends AbstractDesktop {
} }
/** /**
*
* @param taskId * @param taskId
*/ */
public void openTask(int taskId) { public void openTask(int taskId) {
@ -190,7 +185,6 @@ public abstract class TabbedDesktop extends AbstractDesktop {
} }
/** /**
*
* @param url * @param url
* @param title * @param title
* @param closeable * @param closeable
@ -202,7 +196,7 @@ public abstract class TabbedDesktop extends AbstractDesktop {
} }
/** /**
* @param content * @param content HTML content
* @param title * @param title
* @param closeable * @param closeable
*/ */
@ -218,8 +212,7 @@ public abstract class TabbedDesktop extends AbstractDesktop {
} }
/** /**
* * @param fr Iframe
* @param fr
* @param title * @param title
* @param closeable * @param closeable
*/ */
@ -268,7 +261,7 @@ public abstract class TabbedDesktop extends AbstractDesktop {
} }
/** /**
* * Show window in new tab
* @param window * @param window
*/ */
protected void showEmbedded(Window window) protected void showEmbedded(Window window)
@ -328,9 +321,8 @@ public abstract class TabbedDesktop extends AbstractDesktop {
} }
/** /**
*
* @param windowNo * @param windowNo
* @return boolean * @return true if found and close
*/ */
public boolean closeWindow(int windowNo) public boolean closeWindow(int windowNo)
{ {
@ -374,6 +366,9 @@ public abstract class TabbedDesktop extends AbstractDesktop {
{ {
} }
/**
* Runnable to create window content ({@link ADWindow#createPart(Object)})
*/
class OpenWindowRunnable implements Runnable { class OpenWindowRunnable implements Runnable {
private final ADWindow adWindow; private final ADWindow adWindow;
@ -381,6 +376,12 @@ public abstract class TabbedDesktop extends AbstractDesktop {
private final DesktopTabpanel tabPanel; private final DesktopTabpanel tabPanel;
private Callback<ADWindow> callback; private Callback<ADWindow> callback;
/**
* @param adWindow
* @param tab
* @param tabPanel
* @param callback
*/
protected OpenWindowRunnable(ADWindow adWindow, Tab tab, DesktopTabpanel tabPanel, Callback<ADWindow> callback) { protected OpenWindowRunnable(ADWindow adWindow, Tab tab, DesktopTabpanel tabPanel, Callback<ADWindow> callback) {
this.adWindow = adWindow; this.adWindow = adWindow;
this.tab = tab; this.tab = tab;
@ -401,6 +402,10 @@ public abstract class TabbedDesktop extends AbstractDesktop {
} }
} }
/**
* @param title
* @param windowNo
*/
public void setTabTitle(String title, int windowNo) { public void setTabTitle(String title, int windowNo) {
windowContainer.setTabTitle(title, windowNo); windowContainer.setTabTitle(title, windowNo);
} }

View File

@ -51,9 +51,9 @@ import org.zkoss.zul.Menuitem;
import org.zkoss.zul.Style; import org.zkoss.zul.Style;
/** /**
* * Controller for open desktop windows. <br/>
* Implemented using {@link Tabbox}.
* @author Low Heng Sin * @author Low Heng Sin
*
*/ */
public class WindowContainer extends AbstractUIPart implements EventListener<Event> public class WindowContainer extends AbstractUIPart implements EventListener<Event>
{ {

View File

@ -21,8 +21,8 @@ package org.adempiere.webui.util;
public interface IServerPushCallback { public interface IServerPushCallback {
/** /**
* Callback method to perform UI related update. For performance reason, implementation of this method * Callback method to perform UI related update. To keep UI responsive, implementation of this method
* must not perform potentially slow operation. * must not perform potentially slow operation (to avoid holding on to the single Event Listener Thread for too long).
*/ */
public void updateUI(); public void updateUI();