J'ai travaillé sur la création de grille de Sudoku dont la valeur de cellule change chaque fois que je touche une cellule. J'ai donc implémenté cette grille de sudoku dans un LinearLayout by Child View, et j'ai essayé d'utiliser la méthode OnTouch, mais ça ne marche pas. J'ai essayé d'utiliser la méthode log pour vérifier si onTouch est réellement appelé, mais il semble que cette méthode soit parfaitement ignorée. J'ai cherché des solutions sur d'autres questions, mais il semble qu'aucune de ces solutions n'a aidé. Je me sens un peu craint ici, et toute aide serait grandement appréciée.[Android] onTouch dans l'enfant View ne répond pas
Voici mon code:
SudokuActivity.java
package snacker.nonogramsolver;
import ...; /*many things are imported here*/
public class SudokuActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_sudoku);
Button btn = (Button)findViewById(R.id.btn_clear);
Sudoku sdk = new Sudoku(this);
sdk.setOnTouchListener(sdk);
}
}
;
Sudoku.java
package snacker.nonogramsolver;
import ...;
public class Sudoku extends View implements View.OnTouchListener {
int mWidth = 9;
int mHeight = 9;
int mCellWidth, mCellHeight;
int mCellMargin;
int mEdgeThick;
int mStatus;
int mTextSize;
int mXNow = -1, mYNow = -1;
int[][] mBoard = new int[9][9];
Point mBoardPt;
Paint mTextPaint, mTileEdgePaint;
final static int VALID = 0;
public Sudoku(Context context){
super(context);
initializeBoard();
}
public Sudoku(Context context, AttributeSet attrs){
super(context, attrs);
initializeBoard();
}
@Override
protected void onDraw(Canvas canvas){
/* There are some codes here */
Log.d("LogTest","OnDraw Complete");
}
public void initializeBoard(){
for (int x=0; x< mWidth; x++){
for (int y=0; y< mHeight; y++){
mBoard[x][y] = 0;
}
}
invalidate();
}
public boolean onTouch(View v, MotionEvent event){
Log.d("LogTest","Touched?"); /* LOG NOT ACTIVE HERE */
if(event.getAction() == MotionEvent.ACTION_DOWN){
mXNow = getBoardX(event.getX());
Log.d("LogTest","" + mXNow); /* LOG NOT ACTIVE HERE */
mYNow = getBoardY(event.getY());
Log.d("LogTest","" + mYNow); /* LOG NOT ACTIVE HERE */
mBoard[mXNow][mYNow] = mBoard[mXNow][mYNow] + 1;
invalidate();
return true;
}
else return false;
}
int getBoardX(float scrx){
int x = (int)((scrx)/mCellWidth);
if (x < 0) x = 0;
if (x > 8) x= 8;
return x;
}
int getBoardY(float scry){
int y = (int)((scry)/mCellHeight);
if (y < 0) y = 0;
if (y > 8) y = 8;
return y;
}
}
Edit: fichier XML d'activité ajoutée.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:orientation="vertical"
android:id="@+id/activity_sudoku"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="snacker.nonogramsolver.SudokuActivity">
<snacker.nonogramsolver.Sudoku
android:id="@+id/SudokuGrid"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<Button
android:id="@+id/btn_clear"
android:layout_width="150dp"
android:layout_height="30dp"
android:layout_weight="0.06"
android:text="Clear" />
</LinearLayout>
Je suppose que vous devez définir onTouchListener à cette coutume vue Sudoku en activité et gérer la méthode OnTouch() là-bas. Chose est que vous n'avez défini aucun auditeur. btw J'aime votre approche pour en faire une vue personnalisée –
@GauravChauhan J'ai écouteur dans OnCreate dans SudokuActivity. Peut-être que ce n'était pas assez ou mauvaise approche? – SnackerH
essayez de passer le contexte d'activité comme sdk.setOnTouchListener (this), et mettez en œuvre onTouch dans l'activité. –