我制作了一个自定义视图,表示具有其他属性的drawable。
我在FrameLayout内容中添加了更多自定义视图到activity xml。
所以,我在屏幕上有很多自定义视图。这些自定义视图使用包含在db中的数据进行定位,因此是以dinamically方式创建的。
我的目标是点击屏幕上显示的其中一个自定义视图,识别点击的自定义视图并修改drawable。
实际上onClick仅在自定义视图之一上工作,并且点击在所有屏幕中执行,而不仅仅是在自定义视图上。
我测试了更多方法,但这些都没有用。
我的自定义视图:
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;
}
我的活动:
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);
}
}
活动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>
答案 0 :(得分:0)
NodeView
是一个视图,因此它有View.OnClickListener
。您可以为每个View.OnClickListener
实施NodeView
,例如
...
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
}
});
...
}