0

I made a custom view that represent a drawable with other attributes.

I added more of custom views in a FrameLayout content into activity xml.

So, I have a lot of custom views in the screen. These custom views where positioned using the datas contained into db, hence are created dinamically.

My goal is click on one of these custom views represented on the screen, recognize the custom view clicked and modify the drawable.

Actually the onClick worked only on one of custom views and the click perform in all of screen, not only upon the custom view.

I test more ways, but nothing of these worked.

My custom view:

public class NodeView extends View {

private static final String TAG_LOG = NodeView.class.getName();

private String _nodeId;
private int _x;
private int _y;
private float _weight;
private int _type;
private Drawable _nodeDrawable;

private int _usingMode;

private boolean touched;
private boolean mDownTouch;

private OnClickListener _onClickListener;

public void set_onClickListener(OnClickListener _onClickListener) {
    this._onClickListener = _onClickListener;
}

public String get_nodeId() {
    return _nodeId;
}

public void set_nodeId(String _nodeId) {
    this._nodeId = _nodeId;
    invalidate();
    requestLayout();
}

public int get_x() {
    return _x;
}

public void set_x(int _x) {
    this._x = _x;
    invalidate();
    requestLayout();
}

public int get_y() {
    return _y;
}

public void set_y(int _y) {
    this._y = _y;
    invalidate();
    requestLayout();
}

public float get_weight() {
    return _weight;
}

public void set_weight(float _weight) {
    this._weight = _weight;
    invalidate();
    requestLayout();
}

public int get_type() {
    return _type;
}

public void set_type(int _type) {
    this._type = _type;
    invalidate();
    requestLayout();
}

public Drawable get_nodeDrawable() {
    return _nodeDrawable;
}

public void set_nodeDrawable(Drawable _nodeDrawable) {
    this._nodeDrawable = _nodeDrawable;
    invalidate();
    requestLayout();
}

public int get_usingMode() {
    return _usingMode;
}

public void set_usingMode(int _usingMode) {
    this._usingMode = _usingMode;
}

public NodeView(Context context, Node node, int usingMode) {
    super(context);
    init(node, usingMode);
}

private void init(Node node, int usingMode) {
    _nodeId = node.getNodeId();
    Log.d(TAG_LOG, node.toString());
    _x = node.getPosition()[0];
    _y = node.getPosition()[1];
    _weight = node.getWidth();
    _type = node.getType();
    set_usingMode(usingMode);

    // Set the _nodeDrawable depending on node type and using mode
    switch (get_usingMode()) {
        case 0:
            switch (_type) {
                case 0:
                    _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_node_unselected);
                    _nodeDrawable.setBounds(0, 0, 80, 80);
                    break;
                case 1:
                    _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_lift_unselected);
                    _nodeDrawable.setBounds(0, 0, 140, 140);
                    break;
                case 2:
                    _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_wc_unselected);
                    _nodeDrawable.setBounds(0, 0, 115, 115);
                    break;
                case 3:
                    _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_exit_unselected);
                    _nodeDrawable.setBounds(0, 0, 125, 125);
                    break;
            }
            break;
        case 1:
            switch (_type) {
                case 0:
                    _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_node_unselected_nav);
                    _nodeDrawable.setBounds(0, 0, 80, 80);
                    break;
                case 1:
                    _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_lift_unselected_nav);
                    _nodeDrawable.setBounds(0, 0, 140, 140);
                    break;
                case 2:
                    _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_wc_unselected_nav);
                    _nodeDrawable.setBounds(0, 0, 115, 115);
                    break;
                case 3:
                    _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_exit_unselected_nav);
                    _nodeDrawable.setBounds(0, 0, 125, 125);
                    break;
            }
            break;
        case 2:
            switch (_type) {
                case 0:
                    _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_node_unselected_em);
                    _nodeDrawable.setBounds(0, 0, 80, 80);
                    break;
                case 1:
                    _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_lift_unselected_em);
                    _nodeDrawable.setBounds(0, 0, 140, 140);
                    break;
                case 2:
                    _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_wc_unselected_em);
                    _nodeDrawable.setBounds(0, 0, 115, 115);
                    break;
                case 3:
                    _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_exit_unselected_em);
                    _nodeDrawable.setBounds(0, 0, 125, 125);
                    break;
            }
            break;
    }

    touched = false;

    Log.d(TAG_LOG, "Type: " + _type + ", Using Mode: " + String.valueOf(_usingMode));
    invalidate();
}

@Override
protected void onDraw(Canvas canvas) {
    super.onDraw(canvas);

    Log.d(TAG_LOG, "Canvas in");

    switch (_type) {
        case 0:
            canvas.translate((float) _x - 2, (float) _y + 10);
            break;
        case 1:
            canvas.translate((float) _x - 29, (float) _y - 18);
            break;
        case 2:
            canvas.translate((float) _x - 18, (float) _y - 18);
            break;
        case 3:
            canvas.translate((float) _x - 18, (float) _y - 40);
            break;
    }


    Log.d(TAG_LOG, " x short: " + _x + " y short: " + _y);
    Log.d(TAG_LOG, " x float: " + (float) _x + " y float: " + (float) _y);
    if (touched) {
        _nodeDrawable = getResources().getDrawable(R.drawable.ic_node_selected);
        _nodeDrawable.setBounds(0, 0, 140, 140);
        _nodeDrawable.draw(canvas);
    } else {
        // Set the _nodeDrawable depending on node type and using mode
        switch (get_usingMode()) {
            case 0:
                switch (_type) {
                    case 0:
                        _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_node_unselected);
                        _nodeDrawable.setBounds(0, 0, 80, 80);
                        break;
                    case 1:
                        _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_lift_unselected);
                        _nodeDrawable.setBounds(0, 0, 140, 140);
                        break;
                    case 2:
                        _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_wc_unselected);
                        _nodeDrawable.setBounds(0, 0, 115, 115);
                        break;
                    case 3:
                        _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_exit_unselected);
                        _nodeDrawable.setBounds(0, 0, 125, 125);
                        break;
                }
                break;
            case 1:
                switch (_type) {
                    case 0:
                        _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_node_unselected_nav);
                        _nodeDrawable.setBounds(0, 0, 80, 80);
                        break;
                    case 1:
                        _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_lift_unselected_nav);
                        _nodeDrawable.setBounds(0, 0, 140, 140);
                        break;
                    case 2:
                        _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_wc_unselected_nav);
                        _nodeDrawable.setBounds(0, 0, 115, 115);
                        break;
                    case 3:
                        _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_exit_unselected_nav);
                        _nodeDrawable.setBounds(0, 0, 125, 125);
                        break;
                }
                break;
            case 2:
                switch (_type) {
                    case 0:
                        _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_node_unselected_em);
                        _nodeDrawable.setBounds(0, 0, 80, 80);
                        break;
                    case 1:
                        _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_lift_unselected_em);
                        _nodeDrawable.setBounds(0, 0, 140, 140);
                        break;
                    case 2:
                        _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_wc_unselected_em);
                        _nodeDrawable.setBounds(0, 0, 115, 115);
                        break;
                    case 3:
                        _nodeDrawable = getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_exit_unselected_em);
                        _nodeDrawable.setBounds(0, 0, 125, 125);
                        break;
                }
                break;
        }
        _nodeDrawable.draw(canvas);

    }
}

@Override
public boolean onTouchEvent(MotionEvent event) {
    switch (event.getAction()) {
        case MotionEvent.ACTION_DOWN:

            touched = !touched;
            invalidate();

            mDownTouch = true;
            //Toast.makeText(getContext(), String.valueOf(event.getX()) + " " + String.valueOf(event.getY()), Toast.LENGTH_SHORT).show();
            return true;

        case MotionEvent.ACTION_UP:
            if (mDownTouch) {
                mDownTouch = false;
                //performClick(); // Call this method to handle the response, and
                // thereby enable accessibility services to
                // perform this action for a user who cannot
                // click the touchscreen.
                return true;
            }
    }
    performClick();
    return false; // Return false for other touch events
}

@Override
public boolean performClick() {
    Toast.makeText(getContext(), get_nodeId(), Toast.LENGTH_SHORT).show();
    return true;
}

My activity:

    public class MapActivity extends AppCompatActivity {

    private static final String TAG_LOG = it.univpm.idstid.iot4en.MapActivity.class.getName();

    ImageView mapImage;
    public static MenuItem forward;
    public static MenuItem firstPage;

    private String nodeSelected;

    private int _usingMode = 0;

    // _usingMode = 0 indica un utilizzo dell'applicazione non ancora definito, cioè non si sa ancora se verrà utilizzata
    // in modalità navigazione o emergenza

    int initFloorExtra;

    Graph graphFloor;

    private NodeView[] nodeViews;

    ViewGroup nodesContainer;

    public Graph getGraphFloor() {
        return graphFloor;
    }

    public int get_usingMode() {
        return _usingMode;
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_map);


        ActionBar ab = getSupportActionBar();
        ab.setDisplayHomeAsUpEnabled(true);

        Intent inputIntent = getIntent();
        initFloorExtra = inputIntent.getIntExtra("initFloor", 0);
        String floorString = Integer.toString(initFloorExtra);

        mapImage = (ImageView) findViewById(R.id.mapFloor);

        nodesContainer = (ViewGroup) findViewById(R.id.nodesContenitore);

        graphFloor = Graph.Builder.create(this, floorString)
                .build();

        nodeViews = new NodeView[graphFloor.getNodes().size()];
        int i = 0;

        for (Node n : graphFloor.getNodes()) {
            nodeViews[i] = new NodeView(this, n, get_usingMode());
            nodeViews[i].setId(i);
            nodeViews[i].setTag(n.getNodeId());
            FrameLayout.LayoutParams nodeLp = new FrameLayout.LayoutParams(FrameLayout.LayoutParams.WRAP_CONTENT, FrameLayout.LayoutParams.WRAP_CONTENT);
            nodeViews[i].setLayoutParams(nodeLp);
            Log.d(TAG_LOG, nodeLp.toString());
            nodesContainer.addView(nodeViews[i]);

            i++;
        }

        if (initFloorExtra != 0) {
            getSupportActionBar().setTitle(getResources().getString(R.string.floor_pos) + " " + floorString);
        }
        switch (initFloorExtra) {
            case 145:
                mapImage.setImageResource(R.drawable.q145);
                break;
            case 150:
                mapImage.setImageResource(R.drawable.q150);
                break;
            case 155:
                mapImage.setImageResource(R.drawable.q155);
                break;
        }
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.menu_home, menu);
        firstPage = menu.findItem(R.id.firstPage);
        forward = menu.findItem(R.id.forward);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        int itemId = item.getItemId();
        switch (itemId) {
            case R.id.firstPage:
                Intent intent = new Intent(this, InitPositionActivity.class);
                intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK);
                startActivity(intent);
                MapActivity.this.finish();
                break;
            case R.id.forward:
                Intent nextPage = new Intent(this, ModActivity.class);
                nextPage.putExtra("initPos", nodeSelected); //TODO: invece degli intent scrivere su db
                nextPage.putExtra("initFloor", initFloorExtra);
                startActivity(nextPage);
                break;
            case android.R.id.home: // Id relativo alla freccia in alto a sinistra, per tornare alla schermata precedente
                NavUtils.navigateUpFromSameTask(this);
                return true;
        }
        return super.onOptionsItemSelected(item);
    }

}

Activity xml:

    <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:custom="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="@+id/mapactivity"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
android:background="@drawable/background_sfumato"
tools:context="it.univpm.idstid.iot4en.MapActivity">

<ImageView
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:id="@+id/mapFloor"
    android:layout_gravity="center_horizontal"/>

<FrameLayout
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:id="@+id/nodesContenitore">
</FrameLayout>

Bharat
  • 2,441
  • 3
  • 24
  • 36
SeemoneB
  • 1
  • 2

1 Answers1

0

NodeView is a View so it has View.OnClickListener. You can implement View.OnClickListener for each NodeView like

...
for (Node n : graphFloor.getNodes()) {
    nodeViews[i] = new NodeView(this, n, get_usingMode());
    ...
    nodeViews[i].setOnClickListener(new View.OnClickListener() {
        public void onClick(View v) {
            // Perform nodeview on click   
            // as your requirement, modify the drawable here          
        }
    });
    ...
}
Linh
  • 57,942
  • 23
  • 262
  • 279
  • Thank you for your help! I try this way but my problem is that when I try to modify the _nodeDrawable of nodeViews[i], the i must be final. nodeViews[i].set_nodeDrawable(getResources().getDrawable(it.univpm.idstid.ui.R.drawable.ic_node_selected)); – SeemoneB Dec 15 '16 at 01:09