The Artima Developer Community
Jini Corner | ServiceUI | Print | Email | Screen Friendly Version | Previous | Next
Sponsored Link

Version 1.1
The ServiceUI API Specification
by Bill Venners

Revision History

Table of Contents

  1. Introduction
    • 1.1. Direct-Use Clients
    • 1.2. User Adapters
    • 1.3. Jini Service UIs
  2. UI Descriptors
  3. UI Roles
    • 3.1. Displaying Roles to Users
    • 3.2. The net.jini.lookup.ui.MainUI Role
    • 3.3. The net.jini.lookup.ui.AdminUI Role
    • 3.4. The net.jini.lookup.ui.AboutUI Role
    • 3.5. Defining New Role Types
    • 3.6. Working with Existing Role Types
    • 3.7. Choosing Superinterfaces for New Role Types
  4. UI Attributes
    • 4.1. The AccessibleUI Attribute
    • 4.2. The Locales Attribute
    • 4.3. The RequiredPackages Attribute
    • 4.4. The UIFactoryTypes Attribute
  5. UI Factories
    • 5.1. Defining New Factory Types
  6. UI Objects
    • 6.1. What to Provide
    • 6.2. Avoiding Service-Level Data and Client Context
  7. Adding Third-Party UIs
  8. Evolution and Prior Knowledge
  9. Consistent Serialized Forms
  10. Package net.jini.lookup.entry
    • 10.1. Class net.jini.lookup.entry.UIDescriptor
    • 10.2. Class net.jini.lookup.entry.UIDescriptorBean
  11. Package net.jini.lookup.ui
    • 11.1. Summary of Interfaces In Package net.jini.lookup.ui
    • 11.2. Summary of Classes In Package net.jini.lookup.ui
    • 11.3. Summary of Exceptions In Package net.jini.lookup.ui
    • 11.4. Summary of Errors In Package net.jini.lookup.ui
    • 11.5. Interface net.jini.lookup.ui.AboutUI
    • 11.6. Interface net.jini.lookup.ui.AdminUI
    • 11.7. Interface net.jini.lookup.ui.MainUI
  12. Package net.jini.lookup.ui.factory
    • 12.1. Summary of Interfaces In Package net.jini.lookup.ui.factory
    • 12.2. Summary of Classes In Package net.jini.lookup.ui.factory
    • 12.3. Summary of Exceptions In Package net.jini.lookup.ui.factory
    • 12.4. Summary of Errors In Package net.jini.lookup.ui.factory
    • 12.5. Interface net.jini.lookup.ui.factory.DialogFactory
    • 12.6. Interface net.jini.lookup.ui.factory.FrameFactory
    • 12.7. Interface net.jini.lookup.ui.factory.JComponentFactory
    • 12.8. Interface net.jini.lookup.ui.factory.JDialogFactory
    • 12.9. Interface net.jini.lookup.ui.factory.JFrameFactory
    • 12.10. Interface net.jini.lookup.ui.factory.JWindowFactory
    • 12.11. Interface net.jini.lookup.ui.factory.PanelFactory
    • 12.12. Interface net.jini.lookup.ui.factory.WindowFactory
  13. Package net.jini.lookup.ui.attribute
    • 13.1. Summary of Interfaces In Package net.jini.lookup.ui.attribute
    • 13.2. Summary of Classes In Package net.jini.lookup.ui.attribute
    • 13.3. Summary of Exceptions In Package net.jini.lookup.ui.attribute
    • 13.4. Summary of Errors In Package net.jini.lookup.ui.attribute
    • 13.5. Class net.jini.lookup.ui.attribute.AccessibleUI
    • 13.6. Class net.jini.lookup.ui.attribute.Locales
    • 13.7. Class net.jini.lookup.ui.attribute.RequiredPackages
    • 13.8. Class net.jini.lookup.ui.attribute.UIFactoryTypes

1. Introduction

Traditionally, desktop applications are designed with a built-in user interface (UI). The code for the application's UI is often highly coupled to the code that implements the application's functionality. Over time, tentacles of UI code may burrow deep into functionality code, and tentacles of functionality code may burrow back into UI code. In the traditional desktop application, therefore, the UI code and functionality code are usually inseparable, married for all eternity.

Jini's service proxy architecture encourages you to think differently about UI and functionality:

A Jini service proxy should represent the service's pure functionality, expressed via the methods of its object interface. For example, the service proxy interface for a toaster service should express or model the conceptual toaster service's functionality -- the interface should say "what it means to be a toaster." The service proxy should not supply human access to the toaster service; a separate UI object should provide such access.

1.1. Direct-Use Clients

One reason for excluding the UI from the service proxy is to enable client programs (clients) to access the service without human intervention or supervision. Clients written by programmers who knew about a particular service proxy's (potentially well-known or standard) interface can interact with a service directly. As Figure 1 shows, client code can interact directly with a service by invoking the methods in the service proxy interface. Such a client is called a direct-use client, because its programmers, based on their knowledge of the service proxy interface, can write code that uses the service directly via that interface.


Figure 1. A "direct-use" client talks to a service through its object interface.

Direct-use clients need not be completely devoid of a user. For example, a user could operate a device that acts as a direct-use client in certain cases. If the user requested that the device save some data in a file, the device could acquire a storage service proxy and directly invoke methods on that object to save data in a file, without further user intervention. In this case, the user-operated device acts as a direct-use client of storage services, because the device's programmers had prior knowledge of the storage service proxy interface and used that knowledge to program the device to use those services directly.

On the other hand, direct-use clients can also function independently of human supervision or intervention. Such clients act as autonomous agents, which decide for themselves when to enlist a service's help. When an autonomous agent uses a service, it invokes the methods offered by the service proxy interface directly. Thus, an autonomous agent's programmers must have prior knowledge of the service proxy interfaces their agent uses. (Although the human programmer actually has the prior knowledge when he or she writes the client code, in this document the code itself will often be said to have prior knowledge.)

1.2. User Adapters

When you design a Jini service, you should attempt to capture the service's entire functionality in the service proxy interface. To access any aspect of your service, a direct-use client should only need a reference to the service proxy. The service proxy should not include any code that defines a user interface to the service, just code that provides the service functionality at the method invocation level.

To provide a user interface for the service, you should encapsulate the user interface code in a separate UI object. As Figure 2 shows, a UI object grants a user access to some aspect of a Jini service. Think of a service UI object as a user adapter -- an object that adapts a service proxy interface that a human user cannot interact with directly into one a human user can interact with directly. Sitting between the service proxy interface and a human user, a UI object can grant the user access to a service.


Figure 2. A user interacts with a service via a UI object.

A UI object can represent a graphical UI component, such as an AWT Frame or Swing JPanel, but doesn't necessarily need to be graphical. A UI object could also represent a speech interface, a text interface, a speech and graphic combination, or a 3D-immersive world. (The UI object is called UI object, rather than GUI object or view object, because the object represents UI components in general, not just graphical UI components.) Any kind of Jini Service UI, including a 3D-immersible world with speech and virtual text display, should be represented by a UI object, which is distinct from the service proxy.

One advantage of this architecture, in which UI and functionality are separated, is that you can associate multiple UIs with the same service. Associating multiple UIs with one service lets you tailor different UIs for clients that have particular UI capabilities, such as Swing or speech. Clients can then choose the UI that best fits their user interface capabilities. In addition, you may want to associate different UIs that serve different purposes, such as a main UI or an administration UI, with a service. Often, you may need to associate multiple UIs with one Jini service, where each UI has a particular purpose and targets a particular set of client capabilities.

1.3. Jini Service UIs

This specification standardizes how UI providers associate a UI (user adapter) object with a Jini service, and shows how client programs can find the best-fit UI among multiple UIs associated with the same service. To associate a UI with a Jini service, UI providers (primarily service providers, but also possibly third parties) must supply three items:

A UI factory is an object that has one or more factory methods that produce and return a UI object. A UI descriptor, an instance of net.jini.lookup.entry.UIDescriptor (UIDescriptor), serves as a container for the UI factory and other objects that describe the UI produced by the factory. Because UIDescriptor implements net.jini.core.entry.Entry (Entry), you can include a UIDescriptor in a Jini service item's attribute sets array, thereby associating the UI with the service. A UI descriptor contains four public fields:

The attributes, toolkit, and role fields' purpose is to describe the UI produced by the marshalled UI factory. Using these fields, clients can choose from multiple UIs associated with a service. Once they select a UI object, clients can use the other field, factory, to create the object.

To associate a UI with a Jini service, the UI provider must first fill a UI descriptor with a role String, a toolkit String, an attribute set, and a marshalled UI factory. The UI provider must then place the UI descriptor in the attribute sets of the Jini service's service item.

A UI's role indicates both its purpose and its role-related semantics. Each UI role is defined as a Java interface type, which UI objects playing that role implement. The role field references a String whose value is the role interface type's fully qualified name. For example, a net.jini.lookup.ui.MainUI role UI provides general access to a service. A net.jini.lookup.ui.AdminUI role UI enables a user to administer a service. Although most UI object semantics of interest to the client program are defined by the UI factory's return type, some semantics may be tied to the role. For example, for a role that represents a user dialog, the role interface might include methods that let the client determine the dialog's result.

The UI descriptor's attributes field holds a reference to a java.util.Set of serializable objects that contain information about the UI the descriptor represents. These objects can be of any class, so long as they are serializable. Clients can search through the attributes set for attribute types about which they have prior knowledge. The objects can then help the client decide whether or not to use the descriptor-represented UI. Several attribute classes, defined in the net.jini.lookup.ui.attribute package, are described later in this document.

The toolkit field facilitates matching when querying the Jini lookup service. For example, if a client seeks all services that have main UIs working with the Swing toolkit, it could form a net.jini.core.lookup.ServiceItem (ServiceItem) whose attributeSetTemplates array includes a UI descriptor template. If the UI descriptor template's factory and attributes fields are set to null, the role field is set to net.jini.lookup.ui.MainUI, and toolkit field is set to javax.swing, the lookup would only return services that have at least one main UI for Swing.

The factory field contains the UI factory object inside a MarshalledObject so that you can place the class files for the factory and the UI it produces in a different codebase than the service item containing the UI descriptor. By placing the class files for UI factories and UI objects in separate codebases than that of the service item, clients can download a service item without downloading all the JAR files containing those class files, most or all of which the client may never use. Only if the client attempts to use a UI will it need to unmarshal the UI factory; this would trigger the downloading of the JAR file containing the factory class files, and possibly the class files for the factory-generated UI.

To use a UI, a client program must have prior knowledge of both the UI factory type (including, of course, the UI object type returned by its factory methods) and the UI role type. These types define the UI object semantics, which client programmers must understand before they can write code to interact properly with the UI. A client doesn't need prior knowledge of all the attributes types that appear in the attributes set. To the extent the client has prior knowledge of the attribute types, it can use that knowledge to select an appropriate UI from multiple UIs associated with a service.

2. UI Descriptors

A net.jini.lookup.entry.UIDescriptor (UIDescriptor) is a net.jini.core.lookup.Entry (Entry) that enables a UI to be associated with a service in the service item's attribute sets. A UIDescriptor holds a marshalled UI factory object in the factory field, a role type name in the role field, a toolkit package name in the toolkit field, and an attribute set that describes the factory-generated UI in the attributes field.

The UIDescriptor not only houses a marshalled UI factory that produces a UI, but also describes the produced UI to help clients decide whether or not to unmarshal the UI factory. The UI is described in the role, toolkit, and attributes fields.

Class UIDescriptor's public interface looks like this:

package net.jini.lookup.entry;

import java.util.Set;
import java.rmi.MarshalledObject;
import java.io.IOException;

public class UIDescriptor extends net.jini.entry.AbstractEntry {

    public String role;
    public String toolkit;
    public Set attributes;
    public MarshalledObject factory;

    public UIDescriptor() {...}

    public UIDescriptor(String role, String toolkit, Set attributes,
        MarshalledObject factory) {...}

    public final Object getUIFactory(ClassLoader parentLoader)
        throws IOException, ClassNotFoundException {...}
}

Because the marshalled UI factory is referenced from a public field, programs can simply invoke get() directly on the marshalled object to unmarshal the factory client. Clients must ensure, however, that the class loader that loads the class files for the UI can also (likely via a parent class loader) load the class files of the service proxy with which the UI will interact. The UIDescriptor includes a convenience method named getUIFactory() to help clients unmarshal the UI factory with the proper class loader context.

The getUIFactory() method saves a reference to the current context class loader, sets the context class loader to the class loader passed as parentLoader, invokes get() on the marshalled object, then resets the context class loader to the saved reference before returning the object that get() produces.

The class loader passed to the getUIFactory() method in the parentLoader parameter should be able to load types (classes and interfaces) needed when the UI interacts with the role object, which is passed as the first parameter to any factory method. A UI role's semantic description indicates, among other things, what object should be passed to the factory as the role object. For the net.jini.lookup.ui.MainUI role, for example, the role object is the service item. Thus, to unmarshal a UI factory for a main UI, the class loader passed to getUIFactory() should be able to load types needed when the UI interacts with the service proxy contained in the service item. For example, the client could pass to getUIFactory() the class loader the client previously used to load the service proxy.

The String referenced from the toolkit field (which names the main package of the primary UI toolkit) is determined by the UI factory type. Each UI factory type's semantics should include a toolkit string, so UI providers will know what string to put in the toolkit field for their selected UI factory type. Two toolkit strings currently defined are java.awt, for graphical UIs that depend on AWT but not Swing, and javax.swing, for graphical UIs that depend on Swing (and AWT, since Swing is built on top AWT).

3. UI Roles

The UIDescriptor's role field gives the fully qualified name of the interface that represents the role of the UI the marshalled UI factory generates. If the client program unmarshals the UI factory and invokes a factory method, the UI the factory method returns must implement the role interface that role specifies.

For a client program to use a UI, the client must have prior knowledge of the UI semantics, a portion of which the UI's role type defines. Thus, for a client to use a UI, the client must understand the semantics of the type whose fully qualified name appears in the role field of that UI's UIDescriptor.

For example, three role types defined in the net.jini.lookup.ui package by the Jini Service UI Specification are MainUI, for a main UI to a Jini service; AdminUI, for an administration UI; and AboutUI for an about UI. Future incarnations of the Jini Service UI Specification, individual Jini service API specifications, or any other party may define other role types. The UI role types' fully qualified names should, as with any other type, follow the recommended naming convention for unique packages outlined in the Java Language Specification:

You form a unique package name by first having (or belonging to an organization that has) an Internet domain name, such as sun.com. You then reverse this name, component by component, to obtain, in this example, com.sun, and use this as a prefix for your package names, using a convention developed within your organization to further administer package names.

For example, printers in general don't have a main UI, but they may have a UI for printer setup, a UI for print job setup, and a UI for administering the printer. The Printer working group, therefore, could define two role types as part of its Printer API definition, one for printer setup and one for print job setup. (The printer's administration UI could likely use the existing net.jini.lookup.ui.AdminUI role.) The Printer working group would start its role type names with a package prefix it has either received or obtained control over. For example, if the Jini Community grants the Printer working group the right to place its APIs in the net.jini.print package, the group could name its role types: net.jini.print.ui.PrinterSetup and net.jini.print.ui.PrintJobSetup. Each working group or other entity that defines Jini Service APIs can include, as part of its specification, any new UI role types useful in the context of its service.

3.1. Display Roles to Users

As the strings referenced from the role field are Java type names, they should only be manipulated by client programs. Users should not view them. A client may, nevertheless, display localized strings representing roles about which the client has prior knowledge.

For example, imagine a Jini browser client shows a service list using icons and names provided by net.jini.lookup.entry.ServiceType (ServiceType) entries. Such a Jini browser could, when the user double-clicks on a service icon or name, attempt to display a MainUI for the service. In addition, such a Jini browser could, when the user right-clicks on a service icon or name, pop up a list of verb strings, one for each UI role the service offers in a form the client believes it can use. For example, imagine that the user right-clicked, among the UIs offered by the service, three java.swing.JFrame (JFrame) UIs (produced by net.jini.lookup.ui.factory.JFrameFactorys); one for each of net.jini.lookup.ui package's three defined roles: MainUI, AdminUI, and AboutUI. If the client can use JFrames, the client could display three verbs on the pop-up list when the user right-clicks. In the US-English locale, the verb strings could be: "Open...", "Administer...", and "About...". If the user selects About..., the client could display the AboutUI JFrame.

Note that the service did not provide the strings shown to the user -- "Open...", "Administer...", and "About...". The developers of the Jini browser client decided upon these strings. Given that these developers had prior knowledge of the MainUI role, they were able to decide that, in their client, "Open" would be a sensible verb string for MainUIs in the US-English locale. Of course, those developers may have selected other verb strings for other locales. German users of the same browser, for example, could potentially encounter the verb string "Jetzt Geht's Los..." for MainUIs, "Was Ist Das Ding..." for AboutUIs, and "Spielen Sie Mit Die Viele Kleine Nummern..." for AdminUIs.

Because the client program, not the Jini service, provides the verb strings, the client will be unable to show a verb in its list for any role about which it did not have prior knowledge. Thus, if the user right-clicks a service that also offers a JFrame UI with the role net.jini.blender.ui.FrappeUI, the client will be able to display a localized string for that UI in its verb list only if the client's developers had had prior knowledge of that role. If the client's programmers did not endow the program with prior knowledge of FrappeUIs, the client will not be able to list a verb for that UI in its pop-up, and therefore the user will not be able to select it. This prior-knowledge requirement is intentional, because as mentioned previously, the role defines a portion of the UI's semantics. Before the client program can properly use a UI, it must have prior knowledge of the role interface. If a client doesn't know how to use a UI, then letting the user select that UI makes no sense.

3.2. The net.jini.lookup.ui.MainUI Role

net.jini.lookup.ui.MainUI (MainUI) is a UI role interface implemented by main UIs, which enable client programs to grant users general access to a service. If a UI descriptor's UI factory produces a UI that implements this interface (i.e., produces a main UI), the UI descriptor's role field must reference a String with the value net.jini.lookup.ui.MainUI.

The first parameter of any factory method declared in a UI factory type is a role object. Any factory method that produces a main UI must accept as the role object the service item (the net.jini.core.lookup.ServiceItem) of the service associated with the main UI.

Main UIs should let clients configure them before they begin. For example, main UIs produced by FrameFactory, JFrameFactory, WindowFactory and JWindowFactory (all members of the net.jini.lookup.ui.factory package) should not be visible when they return from the factory method. This allows clients to set the UI's position and size, for example, before making the UI visible by invoking setVisible(true) on the UI.

A client should be able to invoke a main UI factory method multiple times sequentially. In other words, if a user uses a service via a main UI, then exits, and then double-clicks once again on the service icon, the client can simply invoke a UI factory method again, and acquire another main UI for the same service. Therefore, you should write main UIs so that they work regardless of the service proxy's state when the main UI is created.

It is recommended that clients use multiple main UIs for the same service only sequentially, and avoid creating for the same service proxy multiple main UIs that operate concurrently with one another. But because some clients may create and use multiple main UIs simultaneously for the same service proxy, service and main UI providers should program defensively to ensure that multiple main UIs for the same service proxy will all work together concurrently.

Here's the net.jini.lookup.ui.MainUI tag interface:

package net.jini.lookup.ui;

public interface MainUI {

    String ROLE = "net.jini.lookup.ui.MainUI";
}

3.3. The net.jini.lookup.ui.AdminUI Role

net.jini.lookup.ui.AdminUI (AdminUI) is a UI role interface implemented by admin UIs, which enable users to administer a service. If a UI descriptor's UI factory produces a UI that implements this interface (i.e., produces an admin UI), the UI descriptor's role field must reference a String with the value "net.jini.lookup.ui.AdminUI".

The first parameter of any factory method declared in a UI factory type is a role object. Any factory method that produces an admin UI must accept as the role object the service item (the net.jini.core.lookup.ServiceItem) of the service associated with the main UI.

Admin UIs have precisely the same semantics as main UIs. The only difference is their purpose. Here's the net.jini.lookup.ui.AdminUI interface:

package net.jini.lookup.ui;

public interface AdminUI {

    String ROLE = "net.jini.lookup.ui.AdminUI";
}

3.4. The net.jini.lookup.ui.AboutUI Role

net.jini.lookup.ui.AboutUI (AboutUI) is a UI role interface implemented by about UIs, which enable users to view (or in some way experience) information about a service. If a UI descriptor's UI factory produces a UI that implements this interface (i.e., produces an about UI), the UI descriptor's role field must reference a String with the value "net.jini.lookup.ui.AboutUI".

The first parameter of any factory method declared in a UI factory type is a role object. Any factory method that produces an about UI must accept as the role object the service item (the net.jini.core.lookup.ServiceItem) of the service associated with the main UI.

About UIs have precisely the same semantics as main UIs. The only difference is their purpose. Here's the net.jini.lookup.ui.AboutUI interface:

package net.jini.lookup.ui;

public interface AboutUI {

    String ROLE = "net.jini.lookup.ui.AboutUI";
}

3.5. Defining New Role Types

As mentioned previously, any party may define new role interfaces. New UI role interfaces will likely be defined in conjunction with new Jini Service API definitions, and many of those roles will likely represent service-specific dialogs with users. As used here, a dialog is a short conversation with the user, usually to obtain some information from the user. Although for graphical toolkits, a dialog is often implemented with a dialog box, such as AWT's Dialog or Swing's JDialog, the term dialog is used here in the generic sense, not strictly in the graphical sense. Service-specific dialog UIs will enable clients to enlist a user's help at various points throughout an otherwise direct use of a service.

As an example, consider a user asking a word processor that has prior knowledge of a well-known Jini Printer API to print a document. (Note that the types appearing in this example were invented for illustration purposes. At the time of this writing, the Jini Printer Service API had not been finalized.) To print via the Jini Print Service API, the word processor first obtains a net.jini.print.service.PrintService (PrintService) object and invokes createPrintJob() on that object to obtain a net.jini.print.job.PrintJob (PrintJob) object. A purely direct-use client must do two things with the PrintJob object -- configure the print job and supply the print data -- before invoking close() on the print job, thereby queuing the printing job. Although the word processor could potentially do both jobs directly, it may not have prior knowledge of the portion of the PrintJob object's interface that lets the client configure the print job, and besides, users are accustomed to configuring print jobs. Given an available user, the word processor would likely want to provide a dialog UI that lets the user configure the print job. Once the user completes his or her configuration and dismisses the dialog UI (with "OK," not "Cancel"), the word processor could supply the print data and invoke close() on the PrintJob.

Given that Jini Print Service API clients would prefer a dialog UI that allows for user configuration, the Printer working group could define a new UI role type for that purpose. The Printer working group would likely place the role interface in some subpackage of its API's main package. For example, it could define an interface named: net.jini.print.ui.PrintJobSetup (PrintJobSetup).

A PrintJobSetup UI would represent a dialog that enables user configuration of a print job, such as page orientation, and so on. Once the user selects configuration parameters, he or she dismisses the dialog UI, which in some way communicates back to the client those parameters (likely by invoking methods on the PrintJob object itself, which is likely the role object for the PrintJobSetup role) and indicates to the client that the dialog is finished. The PrintJobSetup interface's semantics would define how the client interacts with the UI, such as how the client knows the UI has been dismissed, and whether or not the user dismissed the UI with "OK" or "Cancel." If the client receives "OK," the client could then write print data to the PrintJob object and invoke close() on the PrintJob, thereby sending it to the printer.

The semantics of the PrintJobSetup role interface defines the way in which the PrintJobSetup UI interacts with the client (i.e., communicates the configuration data and indicates the dialog's dismissal). As the dialog may require sophisticated UI and client interaction, the role interface may be more than just a tag interface; it may include methods that define how the UI and client interact. The word processor client would know how to display this PrintJobSetup dialog because the PrintJobSetup role interface, and its semantics, would be defined in the Jini Print Service API, of which that client has prior knowledge.

3.6. Working with Existing Role Types

Besides creating new role types for service-specific dialogs, a working group for a Jini service API or a provider of a Jini service API implementation could also provide multiple incarnations of an already-defined role. For example, what if the manufacturer of a combined printer/scanner/faxer/copier product (a "four-in-one box") wanted to deliver four AdminUIs, each dedicated to administering one of four product functions? Such a manufacture could take several approaches.

First, assuming the Jini Community has adopted a standard API for each product function (i.e., a Jini Print Service API, a Jini Scanner Service API, a Jini Faxer Service API, and a Jini Copier Service API), the four-in-one-box manufacturer could, rather than registering one Jini service whose service proxy implements four interfaces (such as Printer, Scanner, Faxer, and Copier), simply offer four separate Jini services, each of which implements only one interface. In this approach, each service could offer an AdminUI dedicated to that one function.

Alternatively (or in addition), the manufacturer could register one Jini service whose service proxy implements all four interfaces. The AdminUI for that service could present a user interface device (such as a tabbed pane for a graphical UI) that lets users select between the four main functions. In this way, one AdminUI exists, which grants users access to the four conceptual administration UIs.

Lastly, the manufacturer could propose to the Jini Community a Jini Four-in-One Service API that includes four new role types, each dedicated to administering a product subset. The Four-in-One working group, which defines the Jini Four-in-One Service API, could control a package that holds the role types, PrinterAdminUI, ScannerAdminUI, FaxerAdminUI, and CopierAdminUI. Clients with prior knowledge of the Jini Four-in-One Service API would also have prior knowledge of the four role types, and therefore could offer verb strings for them. Four-in-One service providers could offer those four admin UI types, but should also offer a basic net.jini.lookup.ui.AdminUI, which as described previously, grants a user access to all four admin UIs. Including an AdminUI lets clients that don't have prior knowledge of the Four-in-One service to offer a UI that will let users administer that service.

3.7. Choosing Superinterfaces for New Role Types

In general, role interfaces should not extend other role interfaces, because only one role interface is described in the UI descriptor's role field. For example, the FaxerAdminUI from the previous section appears to be able to extend AdminUI, because you could consider a FaxerAdminUI to be an AdminUI type. However, only one role interface can appear in the UI descriptor's role field. If a UI is both a FaxerAdminUI and an AdminUI, then which role goes into the role field? If the same UI registers twice, once with AdminUI and once with FaxerAdminUI, then what is the point of FaxerAdminUI? In other words, if a FaxerAdminUI is the default admin UI of the four, then the Four-in-One working group wouldn't need to define a FaxerAdminUI in the first place. They would only need to mention that an AdminUI should behave as an admin UI for the fax machine.

Role interfaces can extend other interfaces; in general, they simply shouldn't extend other role interfaces. If a dialog UI role's semantics are already defined in an interface, then the role interface could extend that interface and thereby inherit those methods and semantics.

Nevertheless, if a party decides to create a role interface that extends another role interface, any factory method that generates the subinterface UI role type must accept the same role object categories accepted by factory methods that generate the superinterface UI role type. For example, if FaxerAdminUI were declared as an AdminUI subinterface, any factory method that produces a FaxerAdminUI would have to accept as the role object the FaxerAdminUI-associated service item, because factory methods that produce AdminUIs accept that role object category.

It is recommended that all role interfaces include a compile time String constant named ROLE, which gives the UI role interface's fully qualified string type name, as it should appear in UI descriptor's role fields. Such convenience constants not only help reduce typing and increase code readability, they also leverage compile-time type checking to help minimize the chance of typographical errors in role strings.

4. UI Attributes

The UI descriptor's attributes field references a java.util.Set of objects that describe the UI generated by the marshalled UI factory. Any object can appear in this set, so long as it is serializable. (Note that if any object in this set is not serializable, the entire set will not appear at the client side -- the UI descriptor's attributes field will be null.)

If a UI provider wishes to register a UI descriptor that has no attributes, it may register the UI descriptor with either a reference to an empty java.util.Set or null in the UI descriptor's attributes field. Nevertheless, because clients would know little about the UI represented by that UI descriptor, many clients would likely ignore the descriptor entirely.

Although all attributes are optional, this specification recommends that all UI descriptors include at least the attributes (all of which are members of the net.jini.lookup.ui.attribute package) described in this list:

The remainder of this section describes these four attribute classes in detail.

4.1. The AccessibleUI Attribute

AccessibleUI indicates that a generated UI implements the javax.accessibility.Accessible interface and that the UI's designer made sure the UI would work well with Java Accessibility API-aware assistive technologies.

The attribute should appear in a UIDescriptor's attributes set only if the marshalled UI factory produces an Accessibility API-supported UI. This attribute's presence in an attributes set means the produced UI will work well with Java Accessibility API-aware assistive technologies.

The AccessibleUI attribute looks like this:

package net.jini.lookup.ui.attribute;

public class AccessibleUI implements java.io.Serializable {
}

4.2. The Locales Attribute

The Locales attribute lists locales supported by a generated UI.

Zero to many Locales instances may appear in a UI descriptor's attributes set. UI providers are encouraged to provide in any UI descriptor's attributes set one Locales object that contains the complete set of locales supported by the UI. Given that UI providers are not required to give complete or even accurate information about locales, clients should program defensively and consider the supported locales a strong hint that locales are supported by the UI, but not necessarily 100 percent complete or accurate.

The public interface of Locales looks like this:

package net.jini.lookup.ui.attribute;

import java.util.Locale;
import java.util.Iterator;
import java.util.Set;
import java.util.List;

public class Locales implements java.io.Serializable {

    public Locales(Set locales) {...}
    public boolean isLocaleSupported(Locale locale) {...}
    public Locale getFirstSupportedLocale(Locale[] locales) {...}
    public Locale getFirstSupportedLocale(List locales) {...}
    public Iterator iterator() {...}
    public Set getLocales() {...}
}

4.3. The RequiredPackages Attribute

RequiredPackages lets clients obtain a list of fully qualified names and version numbers of packages a UI requires.

Zero to many RequiredPackages attributes may appear in a UIDescriptor's attributes set. Client programs interested in a UI may wish to verify that they have all required packages mentioned in the RequiredPackages attributes (if any) before they attempt to create the UI. If the client lacks any required packages (either because the package is absent or because the package is incompatible), the client will not be able to use the UI.

This attribute intends to provide a quick way for a client program to determine that a client cannot use a UI, not to guarantee that a client can definitely use a UI. If a client is missing a required package, or has an incompatible version, the client cannot use the UI. But if the client has compatible versions of all required packages, the client may or may not be able to use the UI.

UI providers should attempt to list in a RequiredPackages attribute all packages that must be installed at the client for the UI to work. In this case, if the client has compatible versions of all listed packages and attempts to generate the UI via the factory method, the client will likely succeed. (Note that packages used by the UI that could potentially be installed at the client, but are also available at the UI's or service's codebase, should not be listed in a RequiredPackages attribute. The client does not actually require such packages, because if the client doesn't have them, it can download the packages.)

Client programmers should bear in mind that a RequiredPackages attribute doesn't necessarily list all required packages. As a result, satisfying all required packages doesn't guarantee the UI will work on the client. Client programs should therefore program defensively. (For example, clients should probably catch LinkageError in appropriate places when dealing with UIs, even if they have compatible versions of all required packages.)

The version numbers listed in RequiredPackages attributes must take the form of specification version numbers, as used by the java.lang.Package class:

Specification version numbers use a "Dewey Decimal" syntax that consists of positive decimal integers separated by periods ".", for example, "2.0" or "1.2.3.4.5.6.7". This allows an extensible number to be used to represent major, minor, micro, etc versions. The version number must begin with a number.

Here's what the RequiredPackages's public interface looks like:

package net.jini.lookup.ui.attribute;

import java.util.Map;
import java.util.Set;
import java.util.Collection;
import java.util.Iterator;

public class RequiredPackages implements java.io.Serializable {

    public RequiredPackages(Map packages) {...}
    public Iterator iterator() {...}
    public String getVersion(String packageName) {...}
    public Map getRequiredPackages() {...}
}

4.4. The UIFactoryTypes Attribute

UIFactoryTypes allows client programs to determine Java types of which a UI factory (marshalled in the same UIDescriptor) is an instance.

Zero to many UIFactoryTypes may appear in the UI descriptor's attributes set. The marshalled UI factory in a UI descriptor's factory field should be an instance of each type that appears in any UIFactoryTypes attribute in that UI descriptor's attributes set.

Of all attributes that could appear in the attributes set, UIFactoryTypes is perhaps the most important. If a UI descriptor's attributes set includes no UIFactoryTypes attribute, then the only way for clients to know what kind of factory a UI descriptor represents is to unmarshal it. But unmarshalling a UI factory will likely involve downloading code, which a client wants to avoid unless it is fairly certain it can use the UI. As a result, UI providers are strongly encouraged to include in every UI descriptor a UIFactoryTypes attribute that includes those Java types (of which the UI factory is an instance) that clients would likely be searching for. In general, clients will be looking for well-known factory interface types, such as those appearing in the net.jini.lookup.ui.factory package.

The public interface of UIFactoryTypes looks like this:

package net.jini.lookup.ui.attribute;

import java.util.Set;
import java.util.Iterator;

public class UIFactoryTypes implements java.io.Serializable {

    public Types(Set typeNames) {...}
    public boolean isAssignableTo(Class classObj) {...}
    public Iterator iterator() {...}
    public Set getTypeNames() {...}
}

5. UI Factories

The UI factory object should implement one or more UI factory interfaces appropriate to the type of UI generated (the factory method's return value) and the options clients have at creation time (the parameters the client can and must pass to the factory method). Factory interfaces can be implemented in many ways, but in general, factory objects should use lazy instantiation of the UI object. For example, rather than instantiating a UI object when the factory instantiates, and returning that already-instantiated UI when a factory method is invoked, a factory object should wait until a factory method is actually invoked before instantiating the UI object. Lazy instantiation lets you marshal the factory object without requiring the UI object's image to be included in the UI factory's marshalled image.

UI factories define methods that indicate by their return type the generated UI's Java type and indicate by their parameters the objects and primitive values that the client can and must supply to the factory. The first parameter to any UI factory method is a role object. The UI's role determines this object's category (but not the type). As used here, category means how the client program obtains the role object. For example, a role might specify that its role object is the service item, the service proxy, or an object obtained by invoking a method on the service proxy. The UI role describes how the client acquires the object that must be passed as the first parameter to the factory method. For example, the MainUI role's semantics indicate that the role object is the service item.

You should write UI factories such that their factory methods can be invoked multiple times. A client may wish to show a user the same UI several times, and therefore may invoke a factory method on the same factory object multiple times. Each time the factory method is invoked, it should produce and return a new UI object copy.

The Jini Service UI API's first version defines eight factory interfaces:

Future incarnations of the Jini Service UI Specification or any other party may define additional UI factory interface types. The fully qualified names of UI factory interface types should, as with any other type, follow the recommended naming convention for unique packages outlined in the Java Language Specification:

You form a unique package name by first having (or belonging to an organization that has) an Internet domain name, such as sun.com. You then reverse this name, component by component, to obtain, in this example, com.sun, and use this as a prefix for your package names, using a convention developed within your organization to further administer package names.

Here's an example UI factory interface:

package net.jini.lookup.ui.factory;

import javax.swing.JFrame;

public interface JFrameFactory extends java.io.Serializable {

    String TOOLKIT = "javax.swing";
    String TYPE_NAME = "net.jini.lookup.ui.factory.JFrameFactory";

    JFrame getJFrame(Object roleObject);
}

Given that only one toolkit field exists, all UIFactory interfaces implemented by a UI factory class must have the same toolkit.

5.1. Defining New Factory Types

Although anyone can define new factory types, to prevent a chaotic explosion of factory types, you should define new factory types with the utmost care. In general, new factory types will be justified only when new UI toolkits appear on the scene. If possible, new factory types should be agreed upon by the Jini Community and placed into the net.jini.lookup.ui.factory package so they are easy to find. For example, if a toolkit is defined for speech-only UIs, a set of factory methods for speech-only UIs could be added to those already in net.jini.lookup.ui.factory. If a graphical toolkit is defined for extremely small screens, a set of factory methods for small-screen UIs could be added to those already in net.jini.lookup.ui.factory.

A UI factory must be an interface, and each method in the interface must take an Object called the roleObject as its first parameter. Other than the role object, nothing should be passed to a factory method except information or context required by the toolkit.

It is recommended that all UI factory interfaces include two compile time String constants:

Such convenience constants not only help reduce typing and increase code readability, they also leverage compile-time type checking to help minimize the chance of typographical errors in toolkit strings and type names added to UIFactoryTypes attributes.

6. UI Objects

UI objects should be user adapters, as shown in Figure 2. Two temptations that service and UI providers may have are:

Both temptations should be avoided. The Jini service proxy should contain the service functionality, the whole service functionality, and nothing but the service functionality. No user-interface code should appear in the service proxy, and no service functionality should appear in the UI object unless it also appears in the service proxy. In short, Jini Service UIs should merely offer users all or part of the functionality available to direct-use clients via the Jini service proxy's methods.

Note that even though the service item may be passed as the role object for some roles -- as it is to factories that produce MainUIs, AdminUIs, and AboutUIs -- the full service functionality should nevertheless be available exclusively through the service proxy. The service item may be passed as the role object to UI factories because extra information (but not extra functionality) could exist elsewhere in the service item, in the service ID or attribute sets, and the UI may wish to display that extra information to the user.

It is strongly encouraged that service and UI providers decouple the class files required by a particular service item from the class files required by any UIs associated with that service via UI descriptors in the service item. If the class files for the service item and those of all service-associated UIs via UI descriptors are placed into the same JAR file, then a client must download all class files for all UIs just to download the service item, even if the client never uses a single UI.

6.1. What to Provide

This specification does not mandate any UI types to be associated with services. Service providers are free to provide any types of UI, or no UIs, with their services. Nevertheless, some discussion of client expectations may help service providers decide what UI types to supply.

First, if a service provider only supplies one UI, it should likely be an embeddable component, such as an AWT Panel or Swing JComponent. Although Swing UIs can be more attractive than AWT UIs, an AWT Panel may allow the greatest reach with one UI type.

A Panel allows clients to show a UI without another pop-up window, whether they support AWT or Swing. If a client wants to pop up a UI, it can embed a Panel UI in a new Frame and pop that up. If a client wants to display a Panel title and icon, it can use the localized name and icon provided by a ServiceType.

A Panel doesn't usually provide an exit for the client, and a menu bar at the top of a Panel is uncommon. So as a UI provider, you may also want to provide either a Frame or a Window in which Panel is placed and add other UI elements, such as menu bar, status bar, and title. If you take this approach, one factory object could implement both the PanelFactory and the FrameFactory interfaces, because their toolkit is the same. This might make sense if the Panel is used in the Frame, and the Frame doesn't require many classes not already used by the panel. Alternatively, you could produce the Panel and Frame by two different UI factories sitting in two different UI descriptors.

You may also wish to support Swing in addition to, or instead of, AWT. If so, at a minimum a Swing JComponent UI, or a JComponent with either a JFrame or a JWindow, may be more suitable. If you take the second approach, one factory object could implement both the JComponentFactory and the JFrameFactory interfaces, because their toolkit is the same. Alternatively, two different UI factories sitting in two different UI descriptors could produce the JComponent and JFrame.

On the other hand, for those UI roles that represent user dialogs, an AWT Dialog or Swing JDialog may be more appropriate.

Currently no direct support exists in the Jini Service UI API for speech-only interfaces, but an AWT or Swing UI could be enhanced with speech capabilities, produced by an appropriate AWT or Swing UI factory type, and identified as speech-enabled with the appropriate required package names (such as javax.speech) in the RequiredPackages attribute. If a speech-enhanced GUI is provided, a GUI-only version should also be provided, as many clients won't have speech capabilities.

6.2. Avoid Service-Level Data and Client Context

Service-level data and client-context data are two data types you may be tempted to pass to UI objects, either directly or via factory methods (which may then tempt you to define new factories). It is strongly recommended that you avoid both temptations.

For example, imagine a service provider requires a user name and password for its service. The service provider wants clients to be able to save a user's name and password locally and enter them automatically the next time the user uses the service. If no user name and password were previously saved, the service UI would prompt the user to type them into a logon dialog box. But if the user name and password were saved, the user would never see the logon dialog box. Rather, the client program would log on automatically with the saved user name and password, and display to the user only the service UI that appears after a successful logon.

To implement this functionality, a service provider might be tempted to define interfaces that allow the client to pass a saved user name and password to the UI. Alternatively, a service provider might be tempted to define new factory methods that enable clients to pass a user name and password to the factory, which could then send them to the UI.

The trouble with either of these approaches is that functionality is being put into the UI that isn't in the service. As mentioned previously, a Jini service's functionality should be modeled in the service proxy, so direct-use client code can just use the service directly. If a service requires a user name and password, the service proxy's interface should allow the client to provide the user name and password. Thus, a client with a user could give the user name and password to the service proxy first, then create the UI. The UI could ask the service proxy if it has a user name and password yet. If not, the UI would show the logon dialog box prompting for the user name and password. Otherwise, the UI wouldn't show the logon dialog box.

The recommended way to design a Jini service and its UIs is to make sure the full functionality is available via the service proxy interface, and keep the UIs focused on being user adapters -- adapting some or all functionality available via the service proxy interface, but offering no more functionality available via the service proxy interface.

Service providers are not the only Jini Community members who will face UI-related temptations in the years ahead; client providers may also be tempted to pass client context data to UI objects.

For example, a client provider wishing to differentiate his or her product from the competition might add a toolbar and status bar to the client program. The client provider might be tempted to define interfaces that allow the client to pass references to the toolbar and status bar to the UI. Alternatively, the client might be tempted to define new factory interfaces whose factory methods include parameters that allow the client to pass references to the toolbar and status bar to the factory, which could then pass it along to the UI. UIs that obtain references to the toolbar and status bar in either of these two ways could then put buttons on the toolbar and write messages to the status bar.

The trouble lurking behind this seemingly innocuous value-add is that the toolbar and status bar references represent client context data, which complicates the UI providers' jobs. If other clients devise their own toolbar and status bar interfaces, and perhaps even up the ante by also defining other client context innovations, UI providers will have to worry about which kinds of client context to support. To the extent a UI provider supports various kinds of client context, that UI provider's test matrix will expand. To the extent that client context becomes complicated, such as the invention of a general compound document model for Jini Service UIs, everyone's job, and the user's experience, become more complicated.

Client providers, therefore, should avoid the temptation to invent client context for Jini Service UIs. The only context data that should be passed to UI factory methods is context a UI toolkit requires, such as the Frame or Window reference required by an AWT Dialog. Similarly, the only context in which Jini Service UIs should be embedded is context the toolkit provides. For example, a client could embed a Jini Service UI JComponent in a JFrame, and then pop up the JFrame. The JComponent's ability to embed is provided by its toolkit, Swing.

UI providers can do their part by ensuring that their UIs don't depend on any context other than that provided by the UI toolkit. Jini Service UIs should be self-contained and care only about the context of their toolkit. If a UI provider wants its UI to write messages to a status bar, the UI should not look for a status bar provided by the client, the UI should itself include a status bar.

7. Add Third-Party UIs

To add a third-party UI to an existing service's attribute sets, you must have the service's cooperation. The service can veto your request at any of several points in the process. The steps are:

  1. Check to see if the service proxy implements net.jini.admin.Administrable (Administrable).

If the service proxy does not implement Administrable, the service provider has already thwarted your wishes. You won't be able to add a third-party UI directly to the service item's attribute sets.

  1. Cast the service proxy to Administrable and invoke getAdmin().
  2. Check to see if the admin object returned by getAdmin() implements the net.jini.admin.JoinAdmin (JoinAdmin).

If the admin object does not implement JoinAdmin, the service provider has thwarted your wishes. You won't be able to add a third-party UI directly to the service item's attribute sets.

  1. Cast the service proxy to JoinAdmin, and invoke appropriate methods to add or modify one or more UIDescriptors.

You add or modify UIDescriptors in the same manner as you would add or modify any kind of Entry in the service's attribute sets. The JoinAdmin's addLookupAttribute() method lets you add new UIDescriptors. Its modifyLookupAttribute() method lets you modify existing UIDescriptors. Once again, the service provider can veto your request, even at this step, by throwing an exception from these methods.

Once a new UIDescriptor for a third-party UI is successfully added via the process described previously, the third party won't need to add it again. From that point forward, whenever a service registers itself with a lookup service, its service item will include the third-party UIDescriptor. It will also reregister itself with any lookup services with which it is currently registered, so that the new UIDescriptor will appear there as well. Even if the service provider crashes and restarts, it should remember the new UIDescriptor and include it in its registrations after the crash and restart.

On the other hand, the UI, UI factory, and possibly the attributes require class files to be available in some codebase. Although the third party never needs to worry about the UIDescriptor being included in future service registrations, the third party must make sure the class files are forever available at some codebase.

One potential problem with adding a third-party UI is that in a strict client-side security policy, downloaded code will by default only have permission to connect back to the host from which the code was downloaded. In that case, if the third-party UI's codebase is on a different host than the service proxy's codebase, the service proxy won't be allowed to talk back to its host at the behest of the UI. Therefore, for a third-party UI to work in practice, either the third-party UI's codebase must be on the same host that serves the service's codebase, or the client must specifically relax its security policy in order to use the third-party UI.

8. Evolution and Prior Knowledge

In the future, the Service UI API can evolve in several different ways. Any party can define new role types and their meanings, new attribute classes, and new factory types. Any party can identify new toolkit types. For clients to be able to use these new types, the new types will need to be publicized. Before a client will be able to use a role, factory, or attribute type, that client's programmers must have had prior knowledge of the type.

Other than service-specific UI roles created under Jini Service APIs, new roles should come from the Service UI project at the Jini Community. Service providers should resist temptation to define new role types, as that complicates clients' jobs. Clients should be able to program to the interface (particular Jini Service APIs about which they have prior knowledge), rather than be forced to program to one or more implementations of that interface. Whether role types are being defined for particular Jini Service APIs, or globally for the Jini Service UI API, the preferred way to define the role interfaces is via the Jini Community Process.

As mentioned previously, new UI factory interface types should be defined with great care. The main justification for a new set of UI factory types is when new UI toolkits appear on the scene. The preferred way to define these interfaces is via the Jini Community Process. Similarly, although anyone can define new attribute types, the preferred way to define these types is through the Jini Community Process.

The Jini Community is the preferred process to define new role, factory, and attribute types because it is the best way to avoid a explosion of types. For example, if a certain attribute type is needed, and twenty different parties define basically the same attribute, but with twenty slightly different names and behaviors, and in twenty different packages, then clients wanting to use that kind of attribute would need to support all twenty variations. It would be far better if those twenty parties agreed on one attribute class. Enabling such collaborations is the Jini Community's main purpose. If twenty parties can agree upon one attribute class, then clients need to be aware of less information (one attribute class versus twenty), and the resulting client programs would likely work more reliably.

9. Consistent Serialized Forms

Because the Jini lookup service uses exact matching of the serialized forms of entry fields, it is critical that fields that will be used in template lookups have serialized forms that are consistent across all virtual machines. However, there is no guarantee that implementations of the Set interface, the declared type of the attributes field of UIDescriptor, have consistent serialized forms across all virtual machines. For example, java.util.HashSet, perhaps the most commonly used implementation of Set, does not guarantee a consistent serialized form. As a result, if a UIDescriptor that contains a HashSet in its attributes field is retrieved from a Jini lookup service, the serialized a form of the attributes field could be different if the UIDescriptor is reserialized as part of a template. This means that a UIDescriptor, when retrieved from a Jini lookup service and used immediately in a lookup template, may not match itself.

The Service UI API was defined under the assumption that UIDescriptors in Jini lookup templates might contain non-null role and toolkit fields, but would always contain null in their attributes and factory fields. It was expected that attributes could be inspected on the client side to select between multiple matches of a Jini lookup. Once a UIDescriptor was selected, it was expected that clients would use the factory field to produce the selected UI. Because of these assumptions, the UIDescriptor class was not designed to ensure a template in which all four fields were non-null would work. In other words, the designers were aware that the attributes field could not be used in lookup templates, but did not imagine that anyone would ever need to do that.

When used in templates intended for basic lookup of Jini services, UIDescriptors will likely never have non-null attributes fields. Nevertheless, UIDescriptors used in templates intended to modify the attribute sets of already-registered Jini services could very likely contain non-null attributes fields. For example, to add an object to the attributes set of a UIDescriptor already registered as part particular Jini service item, you must pass a template UIDescriptor that exactly matches the registered UIDescriptor in the attrSetTemplates parameter of either:

Unfortunately, the use case of modifying a UIDescriptor in an already-registered Jini service item was never considered during the initial design discussions leading to 1.0 release of the Service UI API. To address this need, the 1.1 version of this specification narrows slightly the contracts of these methods and constructors:

The 1.1 specification adds to the contracts of each of these constructors a requirement that they copy the contents of the passed Set or Map into a serializable read-only version that has a consistent serialized form across all VMs. This new requirement yields the desired behavior when attempting to modify UIDescriptors already part of service items registered in lookup services.

10. Package net.jini.lookup.entry

The Service UI API defines two classes, UIDescriptor and UIDescriptorBean, that were placed in a pre-existing package, net.jini.lookup.entry. This specification does not provide a complete specification of the net.jini.lookup.entry package. It does, however, provide a complete specification of classes net.jini.lookup.entry.UIDescriptor and net.jini.lookup.entry.UIDescriptorBean.

10.1. Class net.jini.lookup.entry.UIDescriptor

public class UIDescriptor
     extends net.jini.entry.AbstractEntry

Entry that enables a UI for a service to be associated with the service in the attribute sets of the service item. UIDescriptor holds a marshalled UI factory object, as well as a role string, a sub-role string, and set of attributes that describe the UI generated by the factory.

10.1.1. Constructor UIDescriptor()

public UIDescriptor()

Constructs a UIDescriptor with all fields set to null.

10.1.2. Constructor UIDescriptor(java.lang.String, java.lang.String, java.util.Set, java.rmi.MarshalledObject)

public UIDescriptor(java.lang.String role, java.lang.String toolkit, java.util.Set attributes, java.rmi.MarshalledObject factory)

Constructs a UIDescriptor with the fields set to passed values. This constructor copies the contents of the passed attributes Set into a serializable read-only Set that has a consistent serialized form across all VMs, and initializes the attributes field with the consistent Set.

Parameters:
role - the role
toolkit - the toolkit
attributes - the attributes
factory - the factory

10.1.3. Field role

public role

Gives the fully qualified name of the interface that represents the role of the UI generated by the marshalled UI factory. If the client program unmarshals the UI factory and invokes a factory method, the UI returned by the factory method must implement the role the interface specified by role.

For a client program to be able to use a UI, the client has to have prior knowledge of the UI semantics, which is defined by the UI's role type. Thus, for a client to be able to use a UI, the client must understand the semantics of the type whose fully qualified name is given in the String referenced from the role field of that UI's UIDescriptor.

For example, two role types that are defined in the net.jini.lookup.ui package by the Jini Service UI Specification are MainUI, for a main UI to a Jini service, and AdminUI, for an administration UI. Other role types may be defined by the Jini Service UI Specification and by individual Jini service API specifications.

As the strings referenced from the role field are Java type names, they are intended to be manipulated by client programs only. They should not be shown to a user.

10.1.4. Field toolkit

public toolkit

A String to facilitate searching whose value represents the main UI toolkit (for example Swing or AWT) which the produced UI makes use of. The value to which this field should be set is defined by the semantics of the factory type. (This field is intended to facilitate searches. For example, a client can search for all blender services that have Swing MainUI's.)

10.1.5. Field attributes

public attributes

A set of objects that describe the UI generated by the marshalled UI factory.

10.1.6. Field factory

public factory

The get() method of this MarshalledObject must return an object that implements one or more UI factory interfaces. The actual UI factory type or types implemented by the returned object must be described by a UIFactoryTypes attribute placed in the attributes set of this UIDescriptor.

10.1.7. Method getUIFactory(java.lang.ClassLoader)

public final java.lang.Object getUIFactory(java.lang.ClassLoader parentLoader)
     throws java.io.IOException, java.lang.ClassNotFoundException

A convenience method for unmarshalling the UI factory stored in the MarshalledObject referenced from the factory field. This method saves a reference to the current context class loader, sets the context class loader to the class loader passed as parentLoader, invokes get() on the marshalled object, then resets the context class loader to the saved reference before returning the object produced by get().

The class loader passed in parentLoader should be able to load classes needed when the UI interacts with the roleObject passed as the first parameter to the factory method. For example, if the roleObject is the service item (as it is for the MainUI and AdminUI roles), the class loader passed in parentLoader could be the class loader with which the service proxy object referenced from the service item's service field was loaded. For example:

 Object uiFactory = uiDescriptor.getUIFactory(
     serviceItem.service.getClass().getClassLoader());
 
Throws:
NullPointerException - if parentLoader is null.

10.1.8. Serialized Form of net.jini.lookup.entry.UIDescriptor

10.1.8.1. Serialized Field role

java.lang.String role

Gives the fully qualified name of the interface that represents the role of the UI generated by the marshalled UI factory. If the client program unmarshals the UI factory and invokes a factory method, the UI returned by the factory method must implement the role the interface specified by role.

For a client program to be able to use a UI, the client has to have prior knowledge of the UI semantics, which is defined by the UI's role type. Thus, for a client to be able to use a UI, the client must understand the semantics of the type whose fully qualified name is given in the String referenced from the role field of that UI's UIDescriptor.

For example, two role types that are defined in the net.jini.lookup.ui package by the Jini Service UI Specification are MainUI, for a main UI to a Jini service, and AdminUI, for an administration UI. Other role types may be defined by the Jini Service UI Specification and by individual Jini service API specifications.

As the strings referenced from the role field are Java type names, they are intended to be manipulated by client programs only. They should not be shown to a user.

10.1.8.2. Serialized Field toolkit

java.lang.String toolkit

A String to facilitate searching whose value represents the main UI toolkit (for example Swing or AWT) which the produced UI makes use of. The value to which this field should be set is defined by the semantics of the factory type. (This field is intended to facilitate searches. For example, a client can search for all blender services that have Swing MainUI's.)

10.1.8.3. Serialized Field attributes

java.util.Set attributes

A set of objects that describe the UI generated by the marshalled UI factory.

10.1.8.4. Serialized Field factory

java.rmi.MarshalledObject factory

The get() method of this MarshalledObject must return an object that implements one or more UI factory interfaces. The actual UI factory type or types implemented by the returned object must be described by a UIFactoryTypes attribute placed in the attributes set of this UIDescriptor.

10.2. Class net.jini.lookup.entry.UIDescriptorBean

public class UIDescriptorBean
     extends java.lang.Object
     implements net.jini.lookup.entry.EntryBean, java.io.Serializable

A JavaBeans(TM) component that encapsulates a UIDescriptor object.

10.2.1. Constructor UIDescriptorBean()

public UIDescriptorBean()

Construct a new JavaBeans component, linked to a new empty UIDescriptor object.

10.2.2. Field assoc

protected assoc

The UIDescriptor object associated with this JavaBeans component.

10.2.3. Method makeLink(net.jini.core.entry.Entry)

public void makeLink(net.jini.core.entry.Entry e)

Make a link to a UIDescriptor object.

Parameters:
e - the Entry object, which must be a UIDescriptor, to which to link
Throws:
java.lang.ClassCastException - the Entry is not a UIDescriptor, the correct type for this JavaBeans component

10.2.4. Method followLink()

public net.jini.core.entry.Entry followLink()

Return the UIDescriptor linked to by this JavaBeans component.

10.2.5. Method getRole()

public java.lang.String getRole()

Return the value of the role field in the object linked to by this JavaBeans component.

10.2.6. Method setRole(java.lang.String)

public void setRole(java.lang.String role)

Set the value of the role field in the object linked to by this JavaBeans component.

Parameters:
role - a String specifying the role value

10.2.7. Method getToolkit()

public java.lang.String getToolkit()

Return the value of the toolkit field in the object linked to by this JavaBeans component.

10.2.8. Method setToolkit(java.lang.String)

public void setToolkit(java.lang.String toolkit)

Set the value of the toolkit field in the object linked to by this JavaBeans component.

Parameters:
toolkit - a String specifying the toolkit value

10.2.9. Method getAttributes()

public java.util.Set getAttributes()

Return the value of the attributes field in the object linked to by this JavaBeans component.

10.2.10. Method setAttributes(java.util.Set)

public void setAttributes(java.util.Set attributes)

Set the value of the attributes field in the object linked to by this JavaBeans component.

Parameters:
attributes - a Set specifying the attributes value

10.2.11. Method getFactory()

public java.rmi.MarshalledObject getFactory()

Return the value of the factory field in the object linked to by this JavaBeans component.

10.2.12. Method setFactory(java.rmi.MarshalledObject)

public void setFactory(java.rmi.MarshalledObject factory)

Set the value of the factory field in the object linked to by this JavaBeans component.

Parameters:
factory - a MarshalledObject specifying the factory value

10.2.13. Serialized Form of net.jini.lookup.entry.UIDescriptorBean

10.2.13.1. Serialized Field assoc

net.jini.lookup.entry.UIDescriptor assoc

The UIDescriptor object associated with this JavaBeans component.

11. Package net.jini.lookup.ui

Provides UI role interfaces used to associate service UIs with Jini services.

11.1. Summary of Interfaces In Package net.jini.lookup.ui

11.2. Summary of Classes In Package net.jini.lookup.ui

No classes are declared in package net.jini.lookup.ui.

11.3. Summary of Exceptions In Package net.jini.lookup.ui

No Exceptions are declared in package net.jini.lookup.ui.

11.4. Summary of Errors In Package net.jini.lookup.ui

No Errors are declared in package net.jini.lookup.ui.

11.5. Interface net.jini.lookup.ui.AboutUI

public interface AboutUI

UI role interface implemented by About UIs, which enable users to view (or in some way experience) information about a service. If a UI descriptor's UI factory produces a UI that implements this interface (i.e., produces a About UI), the UI descriptor's role field must reference a String with the value "net.jini.lookup.ui.AboutUI".

The first parameter of any factory method declared in a UI factory type is an object called the "role object." Any factory method that produces an About UI must accept as the role object the service item (the net.jini.core.lookup.ServiceItem) of the service with which the About UI is associated.

About UIs should allow clients to configure them before they begin. For example, About UIs produced by FrameFactory, JFrameFactory, WindowFactory and JWindowFactory (all members of the net.jini.lookup.ui.factory package) should not be visible when they are returned from the factory method. This allows clients to set the UI's position and size, for example, before making the UI visible by invoking setVisible(true) on the UI.

A client should be able to invoke a About UI factory method multiple times sequentially. In other words, if a user uses a service via a About UI, then says exit, then double clicks once again on the service icon, the client can just simply invoke a UI factory method again, and get another About UI for the same service. About UIs, therefore, should be written so that they work no matter what state the service object happens to be in when the About UI is created.

It is recommended that clients use multiple About UIs for the same service only sequentially, and avoid creating multiple About UIs for the same service that operate concurrently with one another. But because some clients may create and use multiple About UIs at the same time for the same service, providers of services and About UIs should program defensively, to ensure that multiple About UIs for the same service at the same time will all work together concurrently.

11.5.1. Field ROLE

public static final ROLE

Convenience constant to use in the role field of UIDescriptors for AboutUI role UIs. The value of this constant is "net.jini.lookup.ui.AboutUI".

11.6. Interface net.jini.lookup.ui.AdminUI

public interface AdminUI

UI role interface implemented by Admin UIs, which enable users to administer a service. If a UI descriptor's UI factory produces a UI that implements this interface (i.e., produces a Admin UI), the UI descriptor's role field must reference a String with the value "net.jini.lookup.ui.AdminUI".

The first parameter of any factory method declared in a UI factory type is an object called the "role object." Any factory method that produces an Admin UI must accept as the role object the service item (the net.jini.core.lookup.ServiceItem) of the service with which the Admin UI is associated.

Admin UIs should allow clients to configure them before they begin. For example, Admin UIs produced by FrameFactory, JFrameFactory, WindowFactory and JWindowFactory (all members of the net.jini.lookup.ui.factory package) should not be visible when they are returned from the factory method. This allows clients to set the UI's position and size, for example, before making the UI visible by invoking setVisible(true) on the UI.

A client should be able to invoke a Admin UI factory method multiple times sequentially. In other words, if a user uses a service via a Admin UI, then says exit, then double clicks once again on the service icon, the client can just simply invoke a UI factory method again, and get another Admin UI for the same service. Admin UIs, therefore, should be written so that they work no matter what state the service object happens to be in when the Admin UI is created.

It is recommended that clients use multiple Admin UIs for the same service only sequentially, and avoid creating multiple Admin UIs for the same service that operate concurrently with one another. But because some clients may create and use multiple Admin UIs at the same time for the same service, providers of services and Admin UIs should program defensively, to ensure that multiple Admin UIs for the same service at the same time will all work together concurrently.

11.6.1. Field ROLE

public static final ROLE

Convenience constant to use in the role field of UIDescriptors for AdminUI role UIs. The value of this constant is "net.jini.lookup.ui.AdminUI".

11.7. Interface net.jini.lookup.ui.MainUI

public interface MainUI

UI role interface implemented by Main UIs, which enable client programs to grant users general access to a service. If a UI descriptor's UI factory produces a UI that implements this interface (i.e., produces a Main UI), the UI descriptor's role field must reference a String with the value "net.jini.lookup.ui.MainUI".

The first parameter of any factory method declared in a UI factory type is an object called the "role object." Any factory method that produces an Main UI must accept as the role object the service item (the net.jini.core.lookup.ServiceItem) of the service with which the Main UI is associated.

Main UIs should allow clients to configure them before they begin. For example, Main UIs produced by FrameFactory, JFrameFactory, WindowFactory and JWindowFactory (all members of the net.jini.lookup.ui.factory package) should not be visible when they are returned from the factory method. This allows clients to set the UI's position and size, for example, before making the UI visible by invoking setVisible(true) on the UI.

A client should be able to invoke a Main UI factory method multiple times sequentially. In other words, if a user uses a service via a Main UI, then says exit, then double clicks once again on the service icon, the client can just simply invoke a UI factory method again, and get another Main UI for the same service. Main UIs, therefore, should be written so that they work no matter what state the service object happens to be in when the Main UI is created.

It is recommended that clients use multiple Main UIs for the same service only sequentially, and avoid creating multiple Main UIs for the same service that operate concurrently with one another. But because some clients may create and use multiple Main UIs at the same time for the same service, providers of services and main UIs should program defensively, to ensure that multiple Main UIs for the same service at the same time will all work together concurrently.

11.7.1. Field ROLE

public static final ROLE

Convenience constant to use in the role field of UIDescriptors for MainUI role UIs. The value of this constant is "net.jini.lookup.ui.MainUI".

12. Package net.jini.lookup.ui.factory

Provides UI factory interfaces used to associate service UIs with Jini services.

12.1. Summary of Interfaces In Package net.jini.lookup.ui.factory

12.2. Summary of Classes In Package net.jini.lookup.ui.factory

No classes are declared in package net.jini.lookup.ui.factory.

12.3. Summary of Exceptions In Package net.jini.lookup.ui.factory

No Exceptions are declared in package net.jini.lookup.ui.factory.

12.4. Summary of Errors In Package net.jini.lookup.ui.factory

No Errors are declared in package net.jini.lookup.ui.factory.

12.5. Interface net.jini.lookup.ui.factory.DialogFactory

public interface DialogFactory
     extends java.io.Serializable

UI factory for a modal or non-modal AWT Dialog with a predetermined title.

If the UI generated by the method declared in this interface implements javax.accessibility.Accessible and supports the Java Accessibility API, an AccessibleUI attribute should be placed in the UIDescriptor's attributes set.

12.5.1. Field TOOLKIT

public static final TOOLKIT

Convenience constant to use in the toolkit field of UIDescriptors that contain a DialogFactory. The value of this constant is "java.awt".

12.5.2. Field TYPE_NAME

public static final TYPE_NAME

Convenience constant to use in the UIFactoryTypes set in the attributes set of UIDescriptors that contain a DialogFactory. The value of this constant is "net.jini.lookup.ui.factory.DialogFactory".

12.5.3. Method getDialog(java.lang.Object, java.awt.Dialog)

public java.awt.Dialog getDialog(java.lang.Object roleObject, java.awt.Dialog owner)

Returns a non-modal Dialog with predetermined title and the specified owner Dialog.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)
owner - the Dialog to act as owner of the returned Dialog

12.5.4. Method getDialog(java.lang.Object, java.awt.Frame)

public java.awt.Dialog getDialog(java.lang.Object roleObject, java.awt.Frame owner)

Returns a non-modal Dialog with predetermined title and the specified owner Frame.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)
owner - the Frame to act as owner of the returned Dialog

12.5.5. Method getDialog(java.lang.Object, java.awt.Dialog, boolean)

public java.awt.Dialog getDialog(java.lang.Object roleObject, java.awt.Dialog owner, boolean modal)

Returns a Dialog with predetermined title and the specified modality and owner Dialog.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)
owner - the Dialog to act as owner of the returned Dialog
modal - if true, the returned Dialog will block input to other windows when shown

12.5.6. Method getDialog(java.lang.Object, java.awt.Frame, boolean)

public java.awt.Dialog getDialog(java.lang.Object roleObject, java.awt.Frame owner, boolean modal)

Returns a Dialog with predetermined title and the specified modality and owner Frame.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)
owner - the Frame to act as owner of the returned Dialog
modal - if true, the returned Dialog will block input to other windows when shown

12.6. Interface net.jini.lookup.ui.factory.FrameFactory

public interface FrameFactory
     extends java.io.Serializable

UI factory for an AWT Frame with a predetermined title.

If the UI generated by the method declared in this interface implements javax.accessibility.Accessible and supports the Java Accessibility API, an AccessibleUI attribute should be placed in the UIDescriptor's attributes set.

12.6.1. Field TOOLKIT

public static final TOOLKIT

Convenience constant to use in the toolkit field of UIDescriptors that contain a FrameFactory. The value of this constant is "java.awt".

12.6.2. Field TYPE_NAME

public static final TYPE_NAME

Convenience constant to use in the UIFactoryTypes set in the attributes set of UIDescriptors that contain a FrameFactory. The value of this constant is "net.jini.lookup.ui.factory.FrameFactory".

12.6.3. Method getFrame(java.lang.Object)

public java.awt.Frame getFrame(java.lang.Object roleObject)

Returns a Frame with predetermined title.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)

12.7. Interface net.jini.lookup.ui.factory.JComponentFactory

public interface JComponentFactory
     extends java.io.Serializable

UI factory for a Swing JComponent.

If the UI generated by the method declared in this interface implements javax.accessibility.Accessible and supports the Java Accessibility API, an AccessibleUI attribute should be placed in the UIDescriptor's attributes set.

12.7.1. Field TOOLKIT

public static final TOOLKIT

Convenience constant to use in the toolkit field of UIDescriptors that contain a JComponentFactory. The value of this constant is "javax.swing".

12.7.2. Field TYPE_NAME

public static final TYPE_NAME

Convenience constant to use in the UIFactoryTypes set in the attributes set of UIDescriptors that contain a JComponentFactory. The value of this constant is "net.jini.lookup.ui.factory.JComponentFactory".

12.7.3. Method getJComponent(java.lang.Object)

public javax.swing.JComponent getJComponent(java.lang.Object roleObject)

Returns a JComponent.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)

12.8. Interface net.jini.lookup.ui.factory.JDialogFactory

public interface JDialogFactory
     extends java.io.Serializable

UI factory for a modal or non-modal Swing JDialog with a predetermined title.

If the UI generated by the method declared in this interface implements javax.accessibility.Accessible and supports the Java Accessibility API, an AccessibleUI attribute should be placed in the UIDescriptor's attributes set.

12.8.1. Field TOOLKIT

public static final TOOLKIT

Convenience constant to use in the toolkit field of UIDescriptors that contain a JDialogFactory. The value of this constant is "javax.swing".

12.8.2. Field TYPE_NAME

public static final TYPE_NAME

Convenience constant to use in the UIFactoryTypes set in the attributes set of UIDescriptors that contain a JDialogFactory. The value of this constant is "net.jini.lookup.ui.factory.JDialogFactory".

12.8.3. Method getJDialog(java.lang.Object)

public javax.swing.JDialog getJDialog(java.lang.Object roleObject)

Returns a non-modal JDialog with predetermined title and no specified owner.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)

12.8.4. Method getJDialog(java.lang.Object, java.awt.Dialog)

public javax.swing.JDialog getJDialog(java.lang.Object roleObject, java.awt.Dialog owner)

Returns a non-modal JDialog with a predetermined title with the specified owner Dialog.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)
owner - the Dialog to act as owner of the returned JDialog

12.8.5. Method getJDialog(java.lang.Object, java.awt.Frame)

public javax.swing.JDialog getJDialog(java.lang.Object roleObject, java.awt.Frame owner)

Returns a non-modal JDialog with a predetermined title with the specified owner Frame.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)
owner - the Frame to act as owner of the returned JDialog

12.8.6. Method getJDialog(java.lang.Object, java.awt.Dialog, boolean)

public javax.swing.JDialog getJDialog(java.lang.Object roleObject, java.awt.Dialog owner, boolean modal)

Returns a JDialog with predetermined title and the specified modality and owner Dialog.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)
owner - the Dialog to act as owner of the returned JDialog
modal - if true, the returned JDialog will block input to other windows when shown

12.8.7. Method getJDialog(java.lang.Object, java.awt.Frame, boolean)

public javax.swing.JDialog getJDialog(java.lang.Object roleObject, java.awt.Frame owner, boolean modal)

Returns a JDialog with predetermined title and the specified modality and owner Frame.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)
owner - the Frame to act as owner of the returned JDialog
modal - if true, the returned JDialog will block input to other windows when shown

12.9. Interface net.jini.lookup.ui.factory.JFrameFactory

public interface JFrameFactory
     extends java.io.Serializable

UI factory for a Swing JFrame with a predetermined title.

If the UI generated by the method declared in this interface implements javax.accessibility.Accessible and supports the Java Accessibility API, an AccessibleUI attribute should be placed in the UIDescriptor's attributes set.

12.9.1. Field TOOLKIT

public static final TOOLKIT

Convenience constant to use in the toolkit field of UIDescriptors that contain a JFrameFactory. The value of this constant is "javax.swing".

12.9.2. Field TYPE_NAME

public static final TYPE_NAME

Convenience constant to use in the UIFactoryTypes set in the attributes set of UIDescriptors that contain a JFrameFactory. The value of this constant is "net.jini.lookup.ui.factory.JFrameFactory".

12.9.3. Method getJFrame(java.lang.Object)

public javax.swing.JFrame getJFrame(java.lang.Object roleObject)

Returns a JFrame with predetermined title.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)

12.10. Interface net.jini.lookup.ui.factory.JWindowFactory

public interface JWindowFactory
     extends java.io.Serializable

UI factory for a Swing JWindow.

If the UI generated by the method declared in this interface implements javax.accessibility.Accessible and supports the Java Accessibility API, an AccessibleUI attribute should be placed in the UIDescriptor's attributes set.

12.10.1. Field TOOLKIT

public static final TOOLKIT

Convenience constant to use in the toolkit field of UIDescriptors that contain a JWindowFactory. The value of this constant is "javax.swing".

12.10.2. Field TYPE_NAME

public static final TYPE_NAME

Convenience constant to use in the UIFactoryTypes set in the attributes set of UIDescriptors that contain a JWindowFactory. The value of this constant is "net.jini.lookup.ui.factory.JWindowFactory".

12.10.3. Method getJWindow(java.lang.Object)

public javax.swing.JWindow getJWindow(java.lang.Object roleObject)

Returns a JWindow with no specified owner.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)

12.10.4. Method getJWindow(java.lang.Object, java.awt.Window)

public javax.swing.JWindow getJWindow(java.lang.Object roleObject, java.awt.Window owner)

Returns a JWindow with specified owner Window.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)
owner - the Window to act as owner of the returned JWindow

12.10.5. Method getJWindow(java.lang.Object, java.awt.Frame)

public javax.swing.JWindow getJWindow(java.lang.Object roleObject, java.awt.Frame owner)

Returns a JWindow with specified owner Frame.

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)
owner - the Frame to act as owner of the returned JWindow

12.11. Interface net.jini.lookup.ui.factory.PanelFactory

public interface PanelFactory
     extends java.io.Serializable

UI factory for an AWT Panel.

If the UI generated by the method declared in this interface implements javax.accessibility.Accessible and supports the Java Accessibility API, an AccessibleUI attribute should be placed in the UIDescriptor's attributes set.

A PreferredTitle may be placed in the attributes set to indicate a preferred title of a pop-up window containing this component.

12.11.1. Field TOOLKIT

public static final TOOLKIT

Convenience constant to use in the toolkit field of UIDescriptors that contain a PanelFactory. The value of this constant is "java.awt".

12.11.2. Field TYPE_NAME

public static final TYPE_NAME

Convenience constant to use in the UIFactoryTypes set in the attributes set of UIDescriptors that contain a JPanelFactory. The value of this constant is "net.jini.lookup.ui.factory.PanelFactory".

12.11.3. Method getPanel(java.lang.Object)

public java.awt.Panel getPanel(java.lang.Object roleObject)

Returns a Panel.

12.12. Interface net.jini.lookup.ui.factory.WindowFactory

public interface WindowFactory
     extends java.io.Serializable

UI factory for an AWT Window that isn't a Frame or a Dialog. AWT Frames should be produced by a FrameFactory. AWT Dialogs should be produced by a DialogFactory.)

If the UI generated by the method declared in this interface implements javax.accessibility.Accessible and supports the Java Accessibility API, an AccessibleUI attribute should be placed in the UIDescriptor's attributes set.

12.12.1. Field TOOLKIT

public static final TOOLKIT

Convenience constant to use in the toolkit field of UIDescriptors that contain a WindowFactory. The value of this constant is "java.awt".

12.12.2. Field TYPE_NAME

public static final TYPE_NAME

Convenience constant to use in the UIFactoryTypes set in the attributes set of UIDescriptors that contain a WindowFactory. The value of this constant is "net.jini.lookup.ui.factory.WindowFactory".

12.12.3. Method getWindow(java.lang.Object, java.awt.Window)

public java.awt.Window getWindow(java.lang.Object roleObject, java.awt.Window owner)

Returns a Window with specified owner Window

Parameters:
roleObject - an object defined by the semantics of the UI role interface implemented by the returned UI object. (UI role is indicated in the role field of UIDescriptors.)
owner - the Window to act as owner of the returned Window

12.12.4. Method getWindow(java.lang.Object, java.awt.Frame)

public java.awt.Window getWindow(java.lang.Object roleObject, java.awt.Frame owner)

Returns a Window with specified owner Frame

Parameters:
owner - the Frame to act as owner of the returned Window

13. Package net.jini.lookup.ui.attribute

Provides attribute classes used to associate service UIs with Jini services.

13.1. Summary of Interfaces In Package net.jini.lookup.ui.attribute

No interfaces are declared in package net.jini.lookup.ui.attribute.

13.2. Summary of Classes In Package net.jini.lookup.ui.attribute

13.3. Summary of Exceptions In Package net.jini.lookup.ui.attribute

No Exceptions are declared in package net.jini.lookup.ui.attribute.

13.4. Summary of Errors In Package net.jini.lookup.ui.attribute

No Errors are declared in package net.jini.lookup.ui.attribute.

13.5. Class net.jini.lookup.ui.attribute.AccessibleUI

public class AccessibleUI
     extends java.lang.Object
     implements java.io.Serializable

UI attribute that indicates a generated UI implements the the javax.accessibility.Accessible interface and that the designer of the UI did the necessary work to make sure the UI would work well with assistive technologies that are aware of the Java Accessibility API.

Only UIDescriptors whose marshalled UI factory produces a UI that supports the Accessibility API should include this attribute. The presence of this attribute in an attribute set means the produced UI will work well with assistive technologies that are aware of the Java Accessibility API.

13.5.1. Constructor AccessibleUI()

public AccessibleUI()

Constructs a new AccessibleUI attribute.

13.5.2. Method equals(java.lang.Object)

public boolean equals(java.lang.Object o)

Compares the specified object (passed in o) with this AccessibleUI object for equality. Returns true if o is non-null and the fully qualified class name of the specified object (passed in o) is the same as the fully qualified class name of this object.

Parameters:
o - the object to compare against

13.5.3. Method hashCode()

public int hashCode()

Returns the hash code value for this AccessibleUI. As all AccessibleUI objects are conceptually equivalent, this method returns the hash code value for this object's fully qualified class name String.

13.5.4. Serialized Form of net.jini.lookup.ui.attribute.AccessibleUI

Serialized form of class net.jini.lookup.ui.attribute.AccessibleUI has no serialized fields.

13.6. Class net.jini.lookup.ui.attribute.Locales

public class Locales
     extends java.lang.Object
     implements java.io.Serializable

UI attribute that lists the locales supported by a generated UI.

13.6.1. Constructor Locales(java.util.Set)

public Locales(java.util.Set locales)

Constructs a Locales using the passed Set. The Set can be mutable or immutable, and must contain only java.util.Locale objects. Each Locale must represent a locale that is supported by the UI generated by the UI factory stored in marshalled form in the same UIDescriptor. This constructor copies the contents of the passed Set into a serializable read-only Set that has a consistent serialized form across all VMs.

Parameters:
locales - A Set of Locale objects. Each element must be non-null and an instance of java.util.Locale.
Throws:
NullPointerException - if locales is null or any element of locales set is null.
IllegalArgumentException - if any non-null element of locales set is not an instance of java.util.Locale.

13.6.2. Method isLocaleSupported(java.util.Locale)

public boolean isLocaleSupported(java.util.Locale locale)

Indicates whether or not a locale is supported by the UI generated by the UI factory stored in the marshalled object of the same UIDescriptor. This method returns true only if the passed Locale exactly matches a Locale supported by the UI, as defined by the equals() method of class java.util.Locale. For example, imagine the UI supports the "en" (General English) locale, but not the "en_US" (US English) locale. Then, if "en_US" is passed to this method, the method will return false.

Parameters:
locale - the locale to check
Throws:
NullPointerException - if locale is null.

13.6.3. Method getFirstSupportedLocale(java.util.Locale[])

public java.util.Locale getFirstSupportedLocale(java.util.Locale[] locales)

Looks through the passed array of Locales (in the order they appear in the array) and returns the first Locale that is supported by the UI (as defined by isLocaleSupported()), or null, if none of the Locales in the passed array are supported by the UI.

Parameters:
locales - an array of locales in order of most desired to least desired
Throws:
NullPointerException - if locales is null.

13.6.4. Method getFirstSupportedLocale(java.util.List)

public java.util.Locale getFirstSupportedLocale(java.util.List locales)

Iterates through the passed List of Locales and returns the first Locale that is supported by the UI (as defined by isLocaleSupported()), or null, if none of the Locales in the passed array are supported by the UI.

Parameters:
locales - a List of locales in order of most desired to least desired
Throws:
NullPointerException - if locales is null.

13.6.5. Method iterator()

public java.util.Iterator iterator()

Returns an iterator over the set of java.util.Locale objects, one for each locale supported by the UI generated by the UI factory stored in the marshalled object of the same UIDescriptor. The returned Iterator does not support remove().

13.6.6. Method getLocales()

public java.util.Set getLocales()

Returns an unmodifiable java.util.Set that contains java.util.Locale objects, one for each locale supported by the UI generated by the UI factory stored in the marshalled object of the same UIDescriptor.

13.6.7. Method equals(java.lang.Object)

public boolean equals(java.lang.Object o)

Compares the specified object (the Object passed in o) with this Locales object for equality. Returns true if the specified object is not null, if the specified object's class is Locales, if the two sets of supported locales are the same size, and if every locale mentioned in the specified Locales object (passed in o) is also mentioned in this Locales object.

Parameters:
o - the object to compare against

13.6.8. Method hashCode()

public int hashCode()

Returns the hash code value for this Locales object.

13.6.9. Serialized Form of net.jini.lookup.ui.attribute.Locales

13.6.9.1. Serialized Field supportedLocales

java.util.Set supportedLocales

A Set of java.util.Locale objects, each of which represents one locale supported by the UI generated by the UI factory stored in marshalled form in the same UIDescriptor.

13.7. Class net.jini.lookup.ui.attribute.RequiredPackages

public class RequiredPackages
     extends java.lang.Object
     implements java.io.Serializable

UI attribute that enables clients to get a list of the fully qualified names and version numbers of packages required by a UI.

One or more RequiredPackages attributes may appear in the attributes of a UIDescriptor. Client programs interested in a UI may wish to verify that they have all required packages mentioned in the RequiredPackages attributes (if any) contained in the UI's UIDescriptor, before they attempt to create the UI. If the client is lacking any required packages (either because the entire package is absent or because the package is present but of an incompatible version), the client will not be able to use the UI,

The intent of this attribute is to provide a quick way for a client program to determine that a UI is unusable by a client, not to grant a guarantee that a UI is definitely usable by the client. If a client is missing a required package, or has an incompatible version of a required package, the client cannot use the UI. But if the client has compatible versions of all required packages listed in a RequiredPackage attribute, the client may or may not be able to use the UI.

UI providers should take bold and valiant strides to list in a RequiredPackage attribute all known packages required of the client, so that if the client discovers it has compatible versions of all listed packages and attempts to generate the UI via the factory method, the client will likely succeed. However, client programmers should bear in mind that a RequiredPackage attribute doesn't necessarily list all required packages. As a result, satisfying all required packages doesn't absolutely guarantee the UI will work on the client. As a result, client programs should program defensively. (For example, clients should probably catch LinkageError in appropriate places when dealing with UIs, even if they find they have compatible versions of all required packages listed in RequiredPackage attributes.) The version numbers must take the form of "specification version numbers," as used by the java.lang.Package class:

Specification version numbers use a "Dewey Decimal" syntax that consists of positive decimal integers separated by periods ".", for example, "2.0" or "1.2.3.4.5.6.7". This allows an extensible number to be used to represent major, minor, micro, etc versions. The version number must begin with a number.

13.7.1. Constructor RequiredPackages(java.util.Map)

public RequiredPackages(java.util.Map packages)

Constructs a RequiredPackages attribute with the passed Map. The keys contained in the passed Map must be Strings that represent fully qualified names of required packages. Each value contained in the passed Map must be the oldest version number of the package (defined by the key) that is compatible with the UI. Version numbers are Strings in the form of "specification version numbers," as used by the java.lang.Package class. This constructor copies the contents of the passed Map into a serializable unmodifiable Map that has a consistent serialized form across all VMs.

Parameters:
packages - a map of String fully qualified names of required packages to String version numbers
Throws:
NullPointerException - if packages is null or if any keys or values contained in packages are null.
IllegalArgumentException - if any non-null key or value contained in packages set is not an instance of java.lang.String.

13.7.2. Method iterator()

public java.util.Iterator iterator()

Returns an iterator over the set of String fully qualified package names required by the UI generated by the UI factory stored in the marshalled object of the same UIDescriptor. The returned Iterator does not support remove().

13.7.3. Method getVersion(java.lang.String)

public java.lang.String getVersion(java.lang.String packageName)

Returns a version number for the required package whose fully qualified package name is passed as the packageName parameter. If the passed String does not represent a required package listed in this RequiredPackage attribute, this method returns null. The version number returned should be a "specification version number," as used by the java.lang.Package class:

Specification version numbers use a "Dewey Decimal" syntax that consists of positive decimal integers separated by periods ".", for example, "2.0" or "1.2.3.4.5.6.7". This allows an extensible number to be used to represent major, minor, micro, etc versions. The version number must begin with a number.
Throws:
NullPointerException - if packageName is null.

13.7.4. Method getRequiredPackages()

public java.util.Map getRequiredPackages()

Returns a java.util.Map whose keys are Strings that represent fully qualified names of required packages and whose values are be the oldest version number of the package (defined by the key) that is compatible with the UI. Version numbers are Strings in the form of "specification version numbers," as used by the java.lang.Package class: The version numbers contained as values in the returned Map should be a "specification version number," as used by the java.lang.Package class:

Specification version numbers use a "Dewey Decimal" syntax that consists of positive decimal integers separated by periods ".", for example, "2.0" or "1.2.3.4.5.6.7". This allows an extensible number to be used to represent major, minor, micro, etc versions. The version number must begin with a number.

13.7.5. Method equals(java.lang.Object)

public boolean equals(java.lang.Object o)

Compares the specified object (the Object passed in o) with this RequiredPackages object for equality. Returns true if the specified object is not null, if the specified object's class is RequiredPackages, if the two sets of package-version pairs are the same size, and if every package-version pair mentioned in the specified RequiredPackages object (passed in o) is also mentioned in this RequiredPackages object.

Parameters:
o - the object to compare against

13.7.6. Method hashCode()

public int hashCode()

Returns the hash code value for this RequiredPackages object.

13.7.7. Serialized Form of net.jini.lookup.ui.attribute.RequiredPackages

13.7.7.1. Serialized Field requiredPackages

java.util.Map requiredPackages

A Map of String keys to String values. The keys contained in the Map must be Strings that represent fully qualified names of required packages. Each value contained in the Map must be the oldest version number of the package (defined by the key) that is compatible with the UI. Version numbers are Strings in the form of "specification version numbers," as used by the java.lang.Package class.

13.8. Class net.jini.lookup.ui.attribute.UIFactoryTypes

public class UIFactoryTypes
     extends java.lang.Object
     implements java.io.Serializable

UI attribute that lists UI factory interfaces of which a UI factory is an instance.

13.8.1. Constructor UIFactoryTypes(java.util.Set)

public UIFactoryTypes(java.util.Set typeNames)

Constructs a UIFactoryTypes attribute using the passed Set. The Set can be mutable or immutable, and must contain only Strings. Each String should represent a fully qualified Java type name of a UI factory interface. This constructor copies the contents of the passed Set into a serializable read-only Set that has a consistent serialized form across all VMs.

The isAssignableTo method of this class will only return true for types whose names are passed explicitly to this constructor via the typeNames parameter. This constructor does not inspect the inheritance hierarchies of the types whose names are passed via the typeNames parameter. It is the client's responsibility to include the name of every UI factory interface of which the relevant UI factory (the UI factory being described by this class) is an instance.

Parameters:
typeNames - A Set of String objects. Each element must be non-null and an instance of java.lang.String.
Throws:
NullPointerException - if typeNames is null or any element of typeNames set is null.
IllegalArgumentException - if any non-null element of typeNames set is not an instance of java.lang.String.

13.8.2. Method isAssignableTo(java.lang.Class)

public boolean isAssignableTo(java.lang.Class classObj)

Returns true if the UI factory (contained in marshalled form in the same UIDescriptor) is an instance of the UI factory interface type passed in parameter classObj. Else, returns false.

This method compares the fully qualified name of the type represented by the passed Class with the fully qualified names of UI factory interfaces implemented by the UI factory's class. If an exact string match is found, this method returns true. If the UI factory is ultimately loaded with a class loader whose parent-delegation chain doesn't include the class loader that defined the passed class, a type with the same name would be loaded into a different namespace of the virtual machine. If so, the two types would be considered different by the virtual machine, even though they shared the same fully qualified name.

Parameters:
classObj - the type to check
Throws:
NullPointerException - if classObj is null

13.8.3. Method iterator()

public java.util.Iterator iterator()

Returns an iterator over the set of types of which a UI factory object is an instance in no particular order. The returned Iterator does not support remove().

13.8.4. Method getTypeNames()

public java.util.Set getTypeNames()

Returns an unmodifiable Set of fully qualified type name Strings of which a UI factory is an instance in no particular order.

13.8.5. Method equals(java.lang.Object)

public boolean equals(java.lang.Object o)

Compares the specified object (the Object passed in o) with this UIFactoryTypes object for equality. Returns true if the specified object is not null, if the specified object's class is UIFactoryTypes, if the two sets of factory types are the same size, and if every factory type mentioned in the specified UIFactoryTypes object (passed in o) is also mentioned in this UIFactoryTypes object.

Parameters:
o - the object to compare against

13.8.6. Method hashCode()

public int hashCode()

Returns the hash code value for this UIFactoryTypes object.

13.8.7. Serialized Form of net.jini.lookup.ui.attribute.UIFactoryTypes

13.8.7.1. Serialized Field typeNames

java.util.Set typeNames

A Set of Strings, each of which represents one fully qualified type name. Each String type name should indicate one UI factory interface implemented by the UI factory contained in marshalled form in the same UIDescriptor in which this UIFactoryTypes appears.

ServiceUI is a trademark of Artima Software, Inc.

Jini Corner | ServiceUI | Print | Email | Screen Friendly Version | Previous | Next

Sponsored Links

Copyright © 1996-2019 Artima, Inc. All Rights Reserved. - Privacy Policy - Terms of Use