Easy to Learn Java: Programming Articles, Examples and Tips

Start with Java in a few days with Java Lessons or Lectures

Home

Code Examples

Java Tools

More Java Tools!

Java Forum

All Java Tips

Books

Submit News
Search the site here...
Search...
 

Swing Chapter 4. (The basics) Layout Managers. Easy for reading, Click here!

Custom Search
Swing Chapter 4. (The basics) Layout Managers. Easy for reading, Click here!

[ Return to Swing (Book) ]

Page: 6/7 



Previous Page Previous Page (5/7) - Next Page (7/7) Next Page
Subpages: 1. Layouts overview 
2. Comparing common layout managers
3.
Using GridBagLayout
4. Choosing the right layout
5. Custom layout manager: part I -Label/field pairs
6. Custom layout manager: part II - Common interfaces
7. Dynamic layout in a JavaBeans container

4.6    Custom layout manager: part II - Common interfaces

In section 4.4 we saw how to choose intermediate containers and appropriate layouts for placing components according to a given specification. This required the use of several intermediate containers and several variants were developed in a search for the best solution. This raises the question: can we somehow just add components one after another to a container which is intelligent enough to lay them out as we would typically expect? The answer is yes, to a certain extent.

In practice the contents of many Java frames and dialogs are constructed using a scheme similar to the following (we realize that this is a big generalization, but you will see these situations arise in many examples throughout this text):

1. Groups (or panels) of controls are laid out in the vertical direction.

2. Labels and their corresponding input fields form two-column structures as described in the previous section.

3. Large components (e.g. lists, tables, text areas, trees, etc.) are usually placed in scroll panes and occupy all space in the horizontal direction.

4. Groups of buttons, including check boxes and radio buttons, are centered in an intermediate container and laid out in the horizontal direction. (In this example we purposefully avoid the vertical placement of buttons for simplicity.)

The example in this section shows how to build a layout manager that places components according to this specification. Its purpose is to further demonstrate that layout managers can be built to define template-like pluggable containers. By adhering to intelligently designed specifications, such templates can be developed to help maximize code reuse and increase productivity. Additionally, in the case of large-scale applications, several different interface designers may consider sharing customized layout managers to enforce interface consistency.

The code below introduces our new custom layout manager, DialogLayout2, which builds upon DialogLayout. To provide boundaries between control groupings, we construct a new component, DialogSeparator. DialogSeparator is simply a label containing text and a horizontal bar that is drawn across the container. Both DialogLayout2 and DialogSeparator are added to our dl package. The FlightReservation class now shows how to construct the sample airline ticket reservation interface we have been working with since section 4.4 using DialogLayout2 and DialogSeparator. In order to comply with our new layout scheme we are forced to place the radio buttons in a row above the list component. The main things to note are that the code involved to build this interface is done with little regard for the existence of a layout manager, and absolutely no intermediate containers are need to be created!

Note: Constructing custom layout managers for use in a single application is not recommended. Only build them when you know that they will be reused again and again to perform common layout tasks. In general, custom layout manager classes belong within custom packages or embedded as inner classes in custom components. They normally do not belong being defined in applications themselves.

Figure 4.17 Using DialogLayout2 custom layout manager.

<<file figure4-17.gif>>

The Code: FlightReservation.java

see \Chapter4\5

import java.awt.*;

import java.awt.event.*;

import javax.swing.*;

import javax.swing.border.*;

import javax.swing.event.*;

import dl.*;

public class FlightReservation extends JFrame

{

  public FlightReservation() {

    super("Flight Reservation Dialog [Custom Layout - 2]");

    Container c = getContentPane();

    c.setLayout(new DialogLayout2(20, 5));

    c.add(new JLabel("Date:"));

    c.add(new JTextField());

    c.add(new JLabel("From:"));

    JComboBox cb1 = new JComboBox();

    cb1.addItem("New York");

    c.add(cb1);

    c.add(new JLabel("To:"));

    JComboBox cb2 = new JComboBox();

    cb2.addItem("London");

    c.add(cb2);

    c.add(new DialogSeparator("Available Flights"));

    JList list = new JList();

    JScrollPane ps = new JScrollPane(list);

    c.add(ps);

    c.add(new DialogSeparator("Options"));

    ButtonGroup group = new ButtonGroup();

    JRadioButton r1 = new JRadioButton("First class");

    group.add(r1);

    c.add(r1);

    JRadioButton r2 = new JRadioButton("Business");

    group.add(r2);

    c.add(r2);

    JRadioButton r3 = new JRadioButton("Coach");

    group.add(r3);

    c.add(r3);

    c.add(new DialogSeparator());

    JButton b1 = new JButton("Search");

    c.add(b1);

    JButton b2 = new JButton("Purchase");

    c.add(b2);

    JButton b3 = new JButton("Exit");

    c.add(b3);

    WindowListener wndCloser = new WindowAdapter() {

      public void windowClosing(WindowEvent e) {

        System.exit(0);

      }

    };

    addWindowListener(wndCloser);

    setVisible(true);

  }

  public static void main(String argv[]) {

    new FlightReservation();

  }

}

The Code: DialogLayout2.java

see \Chapter4\5\dl

package dl;

import java.awt.*;

import java.util.*;

import javax.swing.*;

public class DialogLayout2 implements LayoutManager

{

  protected static final int COMP_TWO_COL = 0;

  protected static final int COMP_BIG = 1;

  protected static final int COMP_BUTTON = 2;

  protected int m_divider = -1;

  protected int m_hGap = 10;

  protected int m_vGap = 5;

  protected Vector m_v = new Vector();

  public DialogLayout2() {}

  public DialogLayout2(int hGap, int vGap) {

    m_hGap = hGap;

    m_vGap = vGap;

  }

  public void addLayoutComponent(String name, Component comp) {}

  public void removeLayoutComponent(Component comp) {}

  public Dimension preferredLayoutSize(Container parent) {

    m_v.removeAllElements();

    int w = 0;

    int h = 0;

    int type = -1;

    for (int k=0 ; k<parent.getComponentCount(); k++) {

      Component comp = parent.getComponent(k);

      int newType = getLayoutType(comp);

      if (k == 0)

        type = newType;

      if (type != newType) {

        Dimension d = preferredLayoutSize(m_v, type);

        w = Math.max(w, d.width);

        h += d.height + m_vGap;

        m_v.removeAllElements();

        type = newType;

      }

      m_v.addElement(comp);

    }

    Dimension d = preferredLayoutSize(m_v, type);

    w = Math.max(w, d.width);

    h += d.height + m_vGap;

    h -= m_vGap;

    Insets insets = parent.getInsets();

    return new Dimension(w+insets.left+insets.right,

      h+insets.top+insets.bottom);

  }

  protected Dimension preferredLayoutSize(Vector v, int type) {

    int w = 0;

    int h = 0;

    switch (type)

    {

      case COMP_TWO_COL:

        int divider = getDivider(v);

        for (int k=1 ; k<v.size(); k+=2) {

          Component comp = (Component)v.elementAt(k);

          Dimension d = comp.getPreferredSize();

          w = Math.max(w, d.width);

          h += d.height + m_vGap;

        }

        h -= m_vGap;

        return new Dimension(divider+w, h);

      case COMP_BIG:

        for (int k=0 ; k<v.size(); k++) {

          Component comp = (Component)v.elementAt(k);

          Dimension d = comp.getPreferredSize();

          w = Math.max(w, d.width);

          h += d.height + m_vGap;

        }

        h -= m_vGap;

        return new Dimension(w, h);

      case COMP_BUTTON:

        Dimension d = getMaxDimension(v);

        w = d.width + m_hGap;

        h = d.height;

        return new Dimension(w*v.size()-m_hGap, h);

    }

    throw new IllegalArgumentException("Illegal type "+type);

  }

  public Dimension minimumLayoutSize(Container parent) {

    return preferredLayoutSize(parent);

  }

  public void layoutContainer(Container parent) {

    m_v.removeAllElements();

    int type = -1;

    Insets insets = parent.getInsets();

    int w = parent.getWidth() - insets.left - insets.right;

    int x = insets.left;

    int y = insets.top;

    for (int k=0 ; k<parent.getComponentCount(); k++) {

      Component comp = parent.getComponent(k);

      int newType = getLayoutType(comp);

      if (k == 0)

        type = newType;

      if (type != newType) {

        y = layoutComponents(m_v, type, x, y, w);

        m_v.removeAllElements();

        type = newType;

      }

      m_v.addElement(comp);

    }

    y = layoutComponents(m_v, type, x, y, w);

    m_v.removeAllElements();

  }

  protected int layoutComponents(Vector v, int type,

   int x, int y, int w)

  {

    switch (type)

    {

      case COMP_TWO_COL:

        int divider = getDivider(v);

        for (int k=1 ; k<v.size(); k+=2) {

          Component comp1 = (Component)v.elementAt(k-1);

          Component comp2 = (Component)v.elementAt(k);

          Dimension d = comp2.getPreferredSize();

          comp1.setBounds(x, y, divider-m_hGap, d.height);

          comp2.setBounds(x+divider, y, w-divider, d.height);

          y += d.height + m_vGap;

        }

        return y;

      case COMP_BIG:

        for (int k=0 ; k<v.size(); k++) {

          Component comp = (Component)v.elementAt(k);

          Dimension d = comp.getPreferredSize();

          comp.setBounds(x, y, w, d.height);

          y += d.height + m_vGap;

        }

        return y;

      case COMP_BUTTON:

        Dimension d = getMaxDimension(v);

        int ww = d.width*v.size() + m_hGap*(v.size()-1);

        int xx = x + Math.max(0, (w - ww)/2);

        for (int k=0 ; k<v.size(); k++) {

          Component comp = (Component)v.elementAt(k);

          comp.setBounds(xx, y, d.width, d.height);

          xx += d.width + m_hGap;

        }

        return y + d.height;

    }

    throw new IllegalArgumentException("Illegal type "+type);

  }

  public int getHGap() { return m_hGap; }

  public int getVGap() { return m_vGap; }

  public void setDivider(int divider) {

    if (divider > 0)

      m_divider = divider;

  }

  public int getDivider() { return m_divider; }

  protected int getDivider(Vector v) {

    if (m_divider > 0)

      return m_divider;

    int divider = 0;

    for (int k=0 ; k<v.size(); k+=2) {

      Component comp = (Component)v.elementAt(k);

      Dimension d = comp.getPreferredSize();

      divider = Math.max(divider, d.width);

    }

    divider += m_hGap;

    return divider;

  }

  protected Dimension getMaxDimension(Vector v) {

    int w = 0;

    int h = 0;

    for (int k=0 ; k<v.size(); k++) {

      Component comp = (Component)v.elementAt(k);

      Dimension d = comp.getPreferredSize();

      w = Math.max(w, d.width);

      h = Math.max(h, d.height);

    }

    return new Dimension(w, h);

  }

  protected int getLayoutType(Component comp) {

    if (comp instanceof AbstractButton)

      return COMP_BUTTON;

    else if (comp instanceof JPanel ||

     comp instanceof JScrollPane ||

     comp instanceof DialogSeparator)

      return COMP_BIG;

    else

      return COMP_TWO_COL;

  }

  public String toString() {

    return getClass().getName() + "[hgap=" + m_hGap + ",vgap="

      + m_vGap + ",divider=" + m_divider + "]";

  }

}

The Code: DialogSeparator.java

see \Chapter4\5\dl

package dl;

import java.awt.*;

import javax.swing.*;

public class DialogSeparator extends JLabel

{

  public static final int OFFSET = 15;

  public DialogSeparator() {}

  public DialogSeparator(String text) { super(text); }

  public Dimension getPreferredSize() {

    return new Dimension(getParent().getWidth(), 20);

  }

  public Dimension getMinimumSize() { return getPreferredSize(); }

  public Dimension getMaximumSize() { return getPreferredSize(); }

  public void paintComponent(Graphics g) {

    super.paintComponent(g);

    g.setColor(getBackground());

    g.fillRect(0, 0, getWidth(), getHeight());

    Dimension d = getSize();

    int y = (d.height-3)/2;

    g.setColor(Color.white);

    g.drawLine(1, y, d.width-1, y);

    y++;

    g.drawLine(0, y, 1, y);

    g.setColor(Color.gray);

    g.drawLine(d.width-1, y, d.width, y);

    y++;

    g.drawLine(1, y, d.width-1, y);

    String text = getText();

    if (text.length()==0)

      return;

    g.setFont(getFont());

    FontMetrics fm = g.getFontMetrics();

    y = (d.height + fm.getAscent())/2;

    int l = fm.stringWidth(text);

    g.setColor(getBackground());

    g.fillRect(OFFSET-5, 0, OFFSET+l, d.height);

    g.setColor(getForeground());

    g.drawString(text, OFFSET, y);

  }

}

Understanding the Code

Class FlightReservation

This variant of our airplane ticket reservation sample application uses an instance of DialogLayout2 as a layout for the whole content pane. Note that no other JPanels are used, and no other layouts are involved. All components are added directly to the content pane and managed by the new layout. This incredibly simplifies the creation of the user interface. Note, however, that we still need to add the label/input field pairs in the correct order because DialogLayout2 manages these pairs identically to DialogLayout.

Note that instances of our DialogSeparator class are used to provide borders between groups of components.

Class DialogLayout2

This class implements the LayoutManager interface to serve as a custom layout manager. It builds on features from DialogLayout to manage all components in its associated container. Three constants declared at the top of the class correspond to the three types of components which are recognized by this layout:

int COMP_TWO_COL: text fields, comboboxes, and their associated labels which must be laid out in two columns using a DialogLayout.

int COMP_BIG: wide components (instances of JPanel, JScrollPane, or DialogSeparator) which must occupy the maximum horizontal container space wherever they are placed.

int COMP_BUTTON: button components (instances of AbstractButton) which must all be given an equal size, laid out in a single row, and centered in the container.

The instance variables used in DialogLayout2 are the same as those used in DialogLayout with one addition: we declare Vector m_v to be used as a temporary collection of components.

To lay out components in a given container we need to determine, for each component, which category it falls under with regard to our DialogLayout2.COMP_XX constants. All components of the same type  added in a contiguous sequence must be processed according to the specific rules described above.

Method preferredLayoutSize() steps through the list of components in a given container and determines their type with our custom getLayoutType() method (see below) and stores it in the newType local variable. Local variable type holds the type of the previous component in the sequence. For the first component in the container, type receives the same value as newType.

  public Dimension preferredLayoutSize(Container parent) {

    m_v.removeAllElements();

    int w = 0;

    int h = 0;

    int type = -1;

    for (int k=0 ; k<parent.getComponentCount(); k++) {

      Component comp = parent.getComponent(k);

      int newType = getLayoutType(comp);

      if (k == 0)

        type = newType;

If we find a break in the sequence of types this triggers a call to the overloaded preferredLayoutSize(Vector v, int type) method (discussed below) which determines the preferred size for a temporary collection of the components stored in the Vector m_v. Then w and h local variables, which are accumulating the total preferred width and height for this layout, are adjusted, and the temporary collection, m_v is cleared. The newly processed component is then added to m_v.

      if (type != newType) {

        Dimension d = preferredLayoutSize(m_v, type);

        w = Math.max(w, d.width);

        h += d.height + m_vGap;

        m_v.removeAllElements();

        type = newType;

      }

      m_v.addElement(comp);

    }

Once our loop finishes we make the unconditional call to preferredLayoutSize() to take into account the last (unprocessed) sequence of components and update h and w accordingly (just as we did in the loop). We then subtract the vertical gap value, m_vGap, from h because we know that we have just processed the last set of components and therefore there is no vertical gap necessary. Taking into account any Insets set on the container, we can now return the computed preferred size as a Dimension instance:

    Dimension d = preferredLayoutSize(m_v, type);

    w = Math.max(w, d.width);

    h += d.height + m_vGap;

    h -= m_vGap;

    Insets insets = parent.getInsets();

    return new Dimension(w+insets.left+insets.right,

      h+insets.top+insets.bottom);

  }

The overloaded method preferredLayoutSize(Vector v, int type) computes the preferred size to lay out a collection of components of a given type. This size is accumulated in w and h local variables. For a collection of type COMP_TWO_COL this method invokes a mechanism that should be familiar (see section 4.5). For a collection of type COMP_BIG this method adjusts the preferable width and increments the height for each component, since these components will be placed in a column:

      case COMP_BIG:

        for (int k=0 ; k<v.size(); k++) {

          Component comp = (Component)v.elementAt(k);

          Dimension d = comp.getPreferredSize();

          w = Math.max(w, d.width);

          h += d.height + m_vGap;

        }

        h -= m_vGap;

        return new Dimension(w, h);

For a collection of type COMP_BUTTON this method invokes our getMaxDimension method (see below) to calculate the desired size of a single component. Since all components of this type will have an equal size and be contained in one single row, the resulting width for this collection is calculated through multiplication by the number of components, v.size():

      case COMP_BUTTON:

        Dimension d = getMaxDimension(v);

        w = d.width + m_hGap;

        h = d.height;

        return new Dimension(w*v.size()-m_hGap, h);

Method layoutContainer(Container parent) assigns bounds to the components in the given container. (Remember that this is the method that actually performs the layout of its associated container.) It processes an array of components similar to the preferredLayoutSize() method. First it steps through the components in the given container, forms a temporarily collection from contiguous components of the same type, and calls the overloaded layoutComponents(Vector v, int type, int x, int y, int w) method to lay out that collection.

Method layoutContainer(Vector v, int type, int x, int y, int w) lays out components from the temporary collection of a given type, starting from the given coordinates x and y, and using the specified width, w, of the container. It returns an adjusted y-coordinate which may be used to lay out a new set of components.

For a collection of type COMP_TWO_COL this method lays out components in two columns identical to how DialogLayout did this (see section 4.5). For a collection of type COMP_BIG the method assigns all available width to each component:

      case COMP_BIG:

        for (int k=0 ; k<v.size(); k++) {

          Component comp = (Component)v.elementAt(k);

          Dimension d = comp.getPreferredSize();

          comp.setBounds(x, y, w, d.height);

          y += d.height + m_vGap;

        }

        return y;

For a collection of type COMP_BUTTON this method assigns an equal size to each component and places them in the center arranged horizontally:

      case COMP_BUTTON:

        Dimension d = getMaxDimension(v);

        int ww = d.width*v.size() + m_hGap*(v.size()-1);

        int xx = x + Math.max(0, (w - ww)/2);

        for (int k=0 ; k<v.size(); k++) {

          Component comp = (Component)v.elementAt(k);

          comp.setBounds(xx, y, d.width, d.height);

          xx += d.width + m_hGap;

        }

        return y + d.height;

Note that a more sophisticated implementation might split a sequence of buttons up into several rows if not enough space is available. We do not do that here to avoid over-complication. This might be an interesting exercise to give you more practice at customizing layout managers.

The remainder of the DialogLayout2 class contains methods which were either explained already, or are simple enough to be considered self-explanatory.

Class DialogSeparator

This class implements a component used to separate two groups of components placed in a column. It extends JLabel to inherit all its default characteristics (font, foreground, etc.). Two available constructors allow the creation of a DialogSeparator with or without a text label.

Method getPreferredSize returns a fixed height, and a width equal to the width of the container. Methods getMinimumSize() and getMaximumSize() simply delegate calls to the getPreferredSize() method.

The paintComponent() method draws a separating bar with a raised appearance across the available component space, and draws the title text (if any) at the left-most side taking into account a pre-defined offset, 15.

Running the Code

At this point you can compile and execute this example. Figure 4.17 shows our sample application which now uses DialogLayout2 to manage the layout of all components. You can see that we have the same set of components placed and sized in accordance with our general layout scheme presented in the beginning of this section. The most important thing to note is that we did not have to use any intermediate containers and layouts to achieve this: all components are added directly to the frame's content pane which is intelligently managed by DialogLayout2.

UI Guideline : Consistency of Button Placement

It is important to be consistent with the placement of buttons in Dialogs and Option Panes. In the example shown here, a symmetrical approach to button placement has been adopted. This is a good safe choice. It ensures balance. With Data Entry Dialogs it is also common to use an asymmetrical layout such as Bottom RHS of the dialog.

In addition to achieving balance with the layout, by being consistent with your placement you allow the User to rely on directional memory to find a specific button location. Directional Memory is strong. Once the User learns where you have placed buttons, they will quickly be able to locate the correct button in many dialog and option situations. It is therefore, vital that you place buttons in a consistent order e.g. OK, Cancel, always and never Cancel, OK.

As a general rule, always use symmetrical layout with option dialogs and be consistent with whatever you decide to use for data entry dialogs.

It makes sense to develop custom components such as JOKCancelButtons and JYesNoButtons. You can then re-use these components every time you need a such a set of buttons. This encapsulates the placement and ensures consistency.



[ Return to Swing (Book) ]


Top 10 read Java Articles
 Get free "1000 Java Tips eBook"

 Java Calendar and Date: good to know facts and code examples

 Array vs ArrayList vs LinkedList vs Vector: an excellent overview and examples

 How can I convert any Java Object into byte array? And byte array to file object

 The Java Lesson 1: What is Java?

 How do I compare two dates and times, date between dates, time between times and

 Maven vs Ant or Ant vs Maven?

 How to open, read, write, close file(s) in Java? Examples on move, rename and de

 Java Array

 Java: JLabel font and color


[ More in News Section ]
Java Lessons

The Java Lesson 1:
What is Java?
The Java Lesson 2:
Anatomy of a simple Java program
The Java Lesson 3:
Identifiers and primitive data types
The Java Lesson 4:
Variables, constants, and literals
The Java Lesson 5:
Arithmetic operations, conversions, and casts
The Java Lesson 6:
Boolean expressions and operations
The Java Lesson 7:
Bitwise operations
The Java Lesson 8:
Flow control with if and else
The Java Lesson 9:
switch statements
The Java Lesson 10:
for, while, and do-while statements
The Java Lesson 11:
Using break and continue
The Java Lesson 12:
Class methods and how they are called
The Java Lesson 13:
Using the Math class
The Java Lesson 14:
Creating and calling custom class methods
The Java Lesson 15:
Overloading class methods
The Java Lesson 16:
An introduction to objects and object references
The Java Lesson 17:
The String class
The Java Lesson 18:
The StringBuffer class
The Java Lesson 19:
Initializing and processing arrays of primitives
The Java Lesson 20:
Initializing and processing arrays of objects
The Java Lesson 23:
Inheritance and overriding inherited methods
The Java Lesson 24:
abstract classes and polymorphism
The Java Lesson 25:
Interfaces, instanceof, and object conversion and casting
The Java Lesson 26:
Introduction to graphical programming and the java.awt packa
The Java Lesson 27:
The Component class
The Java Lesson 28:
Containers and simple layout managers
The Java Lesson 29:
The Color and Font classes
The Java Lesson 30:
Drawing geometric shapes
The Java Lesson 31:
Choice, List, and Checkbox controls
The Java Lesson 32:
Using the Scrollbar graphical control
The Java Lesson 33:
Menus and submenus
The Java Lesson 34:
An introduction to applets and the Applet class
The Java Lesson 35:
Essential HTML to launch an applet and pass it parameters
The Java Lesson 36:
Mouse event processing
Java Lesson 37:
Menus and submenus
Java Lesson 38:
The WindowListener interface and the WindowAdapter class
Java Lesson 39:
An introduction to GridBagLayout
Java Lesson 40:
An introduction to the Java Collections API
Java Lesson 41:
Exception handling with try, catch, and finally blocks
Java Lesson 42:
Claiming and throwing exceptions
Java Lesson 43:
Multithreading, the Thread class, and the Runnable interface
Java Lesson 44:
An introduction to I/O and the File and FileDialog classes
Java Lesson 45:
Low-level and high-level stream classes
Java Lesson 46:
Using the RandomAccessFile class
Java Lessons by
Joh Huhtala: Update

Latest articles
 Java Profiler JProbe to Resolve Performance Problems Faster

 SSL with GlassFish v2, page 5

 SSL with GlassFish v2, page 4

 SSL with GlassFish v2, page 3

 SSL with GlassFish v2, page 2

 The Java Lesson 2: Anatomy of a simple Java program, page 2

 New site about Java for robots and robotics: both software and hardware.

 Exceptions -III: What's an exception and why do I care?

 Exceptions -II: What's an exception and why do I care?

 Exceptions: What's an exception and why do I care?

 Double your Java code quality in 10 minutes, here is receipt

 Murach's Java Servlets and JSP

 How to get ascii code from a char in Java?

 Can we just try without catch? Yes!

 Make Tomcat page load faster

 Make your Tomcat More secure - limit network address for certain IP addresses

 New Java book online starts now here...

 Implementing RESTful Web Services in Java

 Firefox trimming from 1 GB to 40 Mb with many tabs opened

 SSL with GlassFish v2

 My request to replublish Tech Tips

 Search JavaFAQ.nu site here

 New Advanced Installer for Java 6.0 brings XML updates and imports 3rd party MSI

 EJB programming restrictions

 Maven vs Ant or Ant vs Maven?

 Why Java does not use default value which it should?

 How to unsign signed bytes in Java - your guide is here

 The Java Lesson 3: Identifiers and primitive data types. Page 2

 The Java Lesson 7: Bitwise operations with good examples, click here! Page 4

 The Java Lesson 7: Bitwise operations with good examples, click here! Page 3


[ More in News Section ]


Home Code Examples Java Forum All Java Tips Books Submit News, Code... Search... Offshore Software Tech Doodling

RSS feed Java FAQ RSS feed Java FAQ News     

    RSS feed Java Forums RSS feed Java Forums

All logos and trademarks in this site are property of their respective owner. The comments are property of their posters, all the rest 1999-2006 by Java FAQs Daily Tips.

Interactive software released under GNU GPL, Code Credits, Privacy Policy