Question

I'm developing a BlackBerry application which uses table row manager to create a table view. In my application I added bitmap fields as row backgrounds, and then the default blue color of field highlighting was gone. I read some answers in stackoverflow and implemented this code to try to make it highlight in the default color:

        //Adds background image
        final Bitmap bck; 
        bck = Bitmap.getBitmapResource("inner-back-stripe.jpg");
        BitmapField backgrnd = new BitmapField(bck,BitmapField.FOCUSABLE){
            protected void drawFocus(Graphics graphics, boolean on) 
            {
              setSpace(5, 5);
              super.drawFocus(graphics, on);
            } 

        };

but still having the same problem, rows are not highlighted, only texts changes to white color when scrolling.

Sample row background: enter image description here

Here I paste whole code that I have used

public class LeaveDetails extends ListField implements ListFieldCallback  {

    TableRowManager row;
    Vector rows;
    private String[] arrdNames = {"Udith","Mohammadu","Rajaram","David"};
    private String[] arrDate = {"12-Jan-2013","17-Feb-2013","20-Mar-2013","14-May-2013"};
    private String[] arrType = {"Medical Leave","Annual Leave","Medical Leave","Annual Leave"};
    private int[] arrCount = {3,5,2,6};

    public LeaveDetails(){
        super(0, ListField.MULTI_SELECT);
        setRowHeight(100);
        setEmptyString("", DrawStyle.HCENTER);
        setCallback(this);
        rows = new Vector();

        for (int x = 0; x < 4; x++) {
            row = new TableRowManager();
            //Adds background image
            final Bitmap bck;
            bck = Bitmap.getBitmapResource("inner-back-stripe.jpg");
            BitmapField backgrnd = new BitmapField(bck,BitmapField.FOCUSABLE){
                protected void drawFocus(Graphics graphics, boolean on)
                {
                    setSpace(5, 5);
                    super.drawFocus(graphics, on);
                }
            };
            row.add(backgrnd);

            //BitmapField backgrnd = new BitmapField(Bitmap.getBitmapResource("inner-back-stripe.jpg"),Field.FOCUSABLE);
            //row.add(backgrnd); //Field 0

            //Adds names
            LabelField lfName = new LabelField(String.valueOf(arrdNames[x]),FIELD_HCENTER);
            lfName.setFont(lfName.getFont().derive(Font.BOLD,30));
            row.add(lfName);//Field 1

            //Adds date
            LabelField date = new LabelField("Applied on : "+arrDate[x]);
            row.add(date);//Field 2

            //Adds type
            LabelField type = new LabelField("Leave type : "+arrType[x]);
            row.add(type);//Field 3

            //Adds duration in numbers
            LabelField lfCountNotifications = new LabelField(String.valueOf(arrCount[x]),FIELD_HCENTER);
            lfCountNotifications.setFont(lfCountNotifications.getFont().derive(Font.BOLD,72));
            row.add(lfCountNotifications);//Field 4

            //Adds word "Duration"
            LabelField lfNewNotification = new LabelField("Duration/Days",Field.FIELD_HCENTER);
            lfNewNotification.setFont(lfNewNotification.getFont().derive(Font.GEORGIAN_SCRIPT,30));
            row.add(lfNewNotification);//Field 5

            //Adds right arrow image
            BitmapField showMore = new BitmapField(Bitmap.getBitmapResource("more.png"));
            row.add(showMore);//Field 6

            //Adds rows to the table
            rows.addElement(row);
        }//End of the for loop
        setSize(rows.size());
    }

    // ListFieldCallback Implementation
    public void drawListRow(ListField listField, Graphics g, int index, int y,int width) {
        LeaveDetails list = (LeaveDetails) listField;
        TableRowManager rowManager = (TableRowManager) list.rows.elementAt(index);
        rowManager.drawRow(g, 0, y, width, list.getRowHeight());
    }

    //Tracks field click event
    protected boolean trackwheelClick(int status, int time)
    {
        int index = getSelectedIndex();
        switch (index) {
            case 0: Dialog.inform(index+" Clicked");
            break;
            case 1: Dialog.inform(index+" Clicked");
            break;
            case 2: Dialog.inform(index+" Clicked");
            break;
            case 3: Dialog.inform(index+" Clicked");
            break;
            default: Dialog.inform("Error!");
            break;
        }
        return true;
    }

    private class TableRowManager extends Manager {
        public TableRowManager() {
            super(0);
        }

        // Causes the fields within this row manager to be layed out then
        // painted.
        public void drawRow(Graphics g, int x, int y, int width, int height) {
            // Arrange the cell fields within this row manager.
            layout(width, height);
            // Place this row manager within its enclosing list.
            setPosition(x, y);
            // Apply a translating/clipping transformation to the graphics
            // context so that this row paints in the right area.
            g.pushRegion(getExtent());
            // Paint this manager's controlled fields.
            subpaint(g);
            // Restore the graphics context.
            g.popContext();
        }

        // Arrages this manager's controlled fields from left to right within
        // the enclosing table's columns.
        protected void sublayout(int width, int height) {
            // set the size and position of each field.
            int fontHeight = Font.getDefault().getHeight();
            int preferredWidth = getPreferredWidth();

            //Field background image
            Field field = getField(0);
            layoutChild(field, 640, 166);
            setPositionChild(field, 0, 0);

            // Name
            field = getField(1);
            layoutChild(field, 640, fontHeight+4);
            setPositionChild(field, 0, 5);

            // Date
            field = getField(2);
            layoutChild(field, 500, fontHeight+4);
            setPositionChild(field, 0, 30);

            //Type
            field = getField(3);
            layoutChild(field, 500, fontHeight+1);
            setPositionChild(field, 0, 60/*fontHeight+6*/);

            //Duration number
            field = getField(4);
            layoutChild(field, 100, 100);
            setPositionChild(field, 450, 5);

            //"Duration" word
            field = getField(5);
            layoutChild(field, 300, 100);
            setPositionChild(field, 400, 62);

            //More image
            field = getField(6);
            layoutChild(field, 100, 100);
            setPositionChild(field, 575, 20);

            setExtent(preferredWidth, getPreferredHeight());
        }

        // The preferred width of a row is defined by the list renderer.
        public int getPreferredWidth() {
            return 640;
        }

        // The preferred height of a row is the "row height" as defined in the
        // enclosing list.
        public int getPreferredHeight() {
            return getRowHeight();
        }
    }

    public Object get(ListField listField, int index) {
        return null;
    }

    public int getPreferredWidth(ListField listField) {
        return 0;
    }

    public int indexOfList(ListField listField, String prefix, int start) {
        return 0;
    }
}

Does any body have an idea what happened here? I want make it to highlight in default blue color. I'm very much new to BlackBerry.

Was it helpful?

Solution

I think the problem here has to do with the fact that your code uses a BitmapField to produce a background. I would suggest a couple other ways to do it, that will fix your row focus problem.

1. If The Background Must Be A Bitmap

Sometimes, this is necessary. If you have a complicated background design, or special gradient, you may need a background image. For that, I would still remove your BitmapField. So, remove this code:

    final Bitmap bck; 
    bck = Bitmap.getBitmapResource("inner-back-stripe.jpg");
    BitmapField backgrnd = new BitmapField(bck,BitmapField.FOCUSABLE){

do not call add(backgrnd), and then in your sublayout() method, remove this:

    Field field = getField(0);  
    layoutChild(field, 640, 166);  
    setPositionChild(field, 0, 0);  

and finally, remember to change the field index values in the sublayout() method that lays out the other fields (index 1-6 -> 0-5).

Then, create your bitmap background with one extra line of code in your list's constructor:

   public LeaveDetails(){
      super(0, ListField.MULTI_SELECT);
      setRowHeight(100);
      setEmptyString("", DrawStyle.HCENTER);
      setCallback(this);

      setBackground(BackgroundFactory.createBitmapBackground(Bitmap.getBitmapResource("inner-back-stripe.jpg")));

Now, that will create a background for the entire ListField, not just one row. But, in your case, that should work, as your background is just a solid green color.

2. Avoiding Bitmaps Completely

In your situation, I would not recommend a bitmap at all. You're using extra space in your app, and probably hurting performance (slightly) by using a bitmap, when all you want is a solid color background. So, remove the code I told you to remove above, and instead of the setBackground() call I showed in the last code snippet, use this:

   public LeaveDetails(){
      super(0, ListField.MULTI_SELECT);
      setRowHeight(100);
      setEmptyString("", DrawStyle.HCENTER);
      setCallback(this);

      setBackground(BackgroundFactory.createSolidBackground(0xBDCE66));

0xBDCE66 looks like the hex color code for the green you showed in your question.

Row Separators

In your original question, you also showed white separator bars between the rows. My first two solutions won't give you that. But, you can add separators easily to either, by adding a few lines to the drawListRow() method:

public void drawListRow(ListField listField, Graphics g, int index, int y,int width) {
      LeaveDetails list = (LeaveDetails) listField;
      TableRowManager rowManager = (TableRowManager) list.rows
            .elementAt(index);
      rowManager.drawRow(g, 0, y, width, list.getRowHeight());

      // draw a separator of a given color (e.g. white)
      int oldColor = g.getColor();
      g.setColor(Color.WHITE);
      int h = getRowHeight();
      //g.drawLine(0, y+h-1, width, y+h-1);   // for 1 pixel thick line
      g.fillRect(0, y+h-3, width, 3);         // for 3 pixel thick "line"
      g.setColor(oldColor);
}

Results

enter image description here

Note: the right side of each row is hidden because I tested this on a 360px wide screen, and your code hard-codes field locations. So, they're off the right side of the screen. This has nothing to do with the focus highlighting problem, though.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top