I have a Layout in my App Which has 5 Frame Layouts.I have Designed it in the Graphical Layout.It shows Perfect in the layout.But when I Run the App in the Device it is not showing the 2 green buttons with the Keyboard symbol.It Displays Only the Red Area in the App.
I Already Tested the Layout with another Activity.It works perfect.I think there is a Error in the below class.I can't find where it Happens ???
Nothing is shown in the LogCat...
So Help me in the Right Direction :)
Thanks for your Help ...
Layout Code
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent" >
<FrameLayout
android:id="#+id/flKeyboardButton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_centerHorizontal="true"
android:background="#drawable/keyboard_off"
android:maxHeight="100.0dip"
android:maxWidth="60.0dip"
android:minHeight="100.0dip"
android:minWidth="60.0dip" />
<FrameLayout
android:id="#+id/flLeftButton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_alignParentLeft="true"
android:layout_toLeftOf="#id/flKeyboardButton"
android:background="#drawable/left_button_off"
android:maxHeight="100.0dip"
android:minHeight="100.0dip" />
<FrameLayout
android:id="#+id/flRightButton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_alignParentRight="true"
android:layout_toRightOf="#id/flKeyboardButton"
android:background="#drawable/left_button_off"
android:maxHeight="100.0dip"
android:minHeight="100.0dip" />
<FrameLayout
android:id="#+id/flAdvancedPanel"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_alignParentRight="true"
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true"
android:background="#drawable/advanced"
android:maxHeight="96dp" >
</FrameLayout>
<FrameLayout
android:id="#+id/flTouchPad"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_above="#id/flKeyboardButton"
android:layout_alignParentLeft="true"
android:layout_alignParentRight="true"
android:layout_alignParentTop="true"
android:background="#drawable/touchpad" />
<EditText
android:id="#+id/etAdvancedText"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_alignParentRight="true"
android:layout_centerHorizontal="true"
android:layout_marginTop="-100dp"
android:inputType="textMultiLine"
android:maxHeight="32dp"
android:visibility="visible" />
</RelativeLayout>
Here is the Java Code
public class PadActivity extends Activity {
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.fragment_mouse);
Settings.init(this.getApplicationContext());
// Hide the title bar
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN);
if (this.lock == null) {
Context appContext = this.getApplicationContext();
// get wake lock
PowerManager manager = (PowerManager) appContext.getSystemService(Context.POWER_SERVICE);
this.lock = manager.newWakeLock(PowerManager.SCREEN_BRIGHT_WAKE_LOCK, this.getString(R.string.app_name));
// prepare sensor Listener
this.mSensorListener = new SensorEventListener() {
// #Override
public void onSensorChanged(SensorEvent event) {
Sensor sensor = event.sensor;
int type = sensor.getType();
switch (type) {
case Sensor.TYPE_ACCELEROMETER:
onAccelerometer(event.values);
break;
case Sensor.TYPE_MAGNETIC_FIELD:
onMagnetic(event.values);
break;
// case Sensor.TYPE_ORIENTATION:
// break;
}
}
// #Override
public void onAccuracyChanged(Sensor sensor, int accuracy) {
// no use for this
}
};
if (useOrientation) {
// enable Sensors
enableSensors();
}
/**
* Caches information and forces WrappedMotionEvent class to load at
* Activity startup (avoid initial lag on touchpad).
*/
this.mIsMultitouchEnabled = WrappedMotionEvent.isMutitouchCapable();
// Setup accelerations
mMouseSensitivityPower = 1 + ((double) Settings.sensitivity) / 100d;
mScrollStep = (sScrollStepMin - sScrollStepMax) * (sScrollMaxSettingsValue - Settings.scrollSensitivity) / sScrollMaxSettingsValue + sScrollStepMax;
Log.d(TAG, "mScrollStep=" + mScrollStep);
Log.d(TAG, "Settings.sensitivity=" + Settings.scrollSensitivity);
//
this.accel = new Point3D();
this.mag = new Point3D();
this.lastSpace = new CoordinateSpace();
this.currSpace = new CoordinateSpace();
// UI runnables
this.rLeftDown = new Runnable() {
public void run() {
drawButtonOn(flLeftButton);
}
};
this.rLeftUp = new Runnable() {
public void run() {
drawButtonOff(flLeftButton);
}
};
this.rRightDown = new Runnable() {
public void run() {
drawButtonOn(flRightButton);
}
};
this.rRightUp = new Runnable() {
public void run() {
drawButtonOff(flRightButton);
}
};
this.rMidDown = new Runnable() {
public void run() {
drawSoftOn();
}
};
this.rMidUp = new Runnable() {
public void run() {
drawSoftOff();
}
};
// window manager stuff
getWindow().setFlags(32, 32);
// this.getWindow().setFlags(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_PAN,
// WindowManager.LayoutParams.SOFT_INPUT_ADJUST_PAN);
}
//
try {
DisplayMetrics dm = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(dm);
int width = getApplicationContext().getResources().getDisplayMetrics().widthPixels;
int height = getApplicationContext().getResources().getDisplayMetrics().heightPixels;
Log.i("Width", "" + width);
Log.i("height", "" + height);
this.sender = new OSCPortOut(InetAddress.getByName(Settings.ip), OSCPort.defaultSCOSCPort());
//
this.initTouchpad();
this.initLeftButton();
this.initRightButton();
this.initMidButton();
this.initAdvancedPanel();
this.initAdvancedText();
} catch (Exception ex) {
Log.d(TAG, ex.toString());
}
}
private void initTouchpad() {
FrameLayout fl = (FrameLayout) this.findViewById(R.id.flTouchPad);
// let's set up a touch listener
fl.setOnTouchListener(new View.OnTouchListener() {
public boolean onTouch(View v, MotionEvent ev) {
return onMouseMove(ev);
}
});
}
private void initLeftButton() {
FrameLayout fl = (FrameLayout) this.findViewById(R.id.flLeftButton);
android.view.ViewGroup.LayoutParams lp = fl.getLayoutParams();
// if(!Settings.hideMouseButtons) lp.height=0;
fl.setLayoutParams(lp);
// listener
fl.setOnTouchListener(new View.OnTouchListener() {
public boolean onTouch(View v, MotionEvent ev) {
return onLeftTouch(ev);
}
});
this.flLeftButton = fl;
}
private void initRightButton() {
FrameLayout iv = (FrameLayout) this.findViewById(R.id.flRightButton);
android.view.ViewGroup.LayoutParams lp = iv.getLayoutParams();
// if(!Settings.hideMouseButtons) lp.height=0;
iv.setLayoutParams(lp);
// listener
iv.setOnTouchListener(new View.OnTouchListener() {
public boolean onTouch(View v, MotionEvent ev) {
return onRightTouch(ev);
}
});
this.flRightButton = iv;
}
private void initMidButton() {
FrameLayout fl = (FrameLayout) this.findViewById(R.id.flKeyboardButton);
android.view.ViewGroup.LayoutParams lp = fl.getLayoutParams();
// if(!Settings.hideMouseButtons) lp.height=0;
fl.setLayoutParams(lp);
// listener
fl.setOnTouchListener(new View.OnTouchListener() {
public boolean onTouch(View v, MotionEvent ev) {
return onMidTouch(ev);
}
});
this.flMidButton = fl;
}
Its Seems that your java file code is wrong. Your first function should be OnCreate() and rest of the code should be write after that.
Even you have set your view after long code which is totally wrong.
public class PadActivity extends Activity {
// set your variables & objects
..
..
#Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.pad_layout);
...
... //Other code
}
}
Please change your code position that will definitely work.
#id/flTouchPad's height is match_parent, which I think is the problem (it makes the View as big as its parent).
Atlast I Found why the Layout is not shown Properly in my App.
It is Due to the this line in my three Initialization Methods .
if(!Settings.hideMouseButtons) lp.height=0;
After Commenting this Line the layout shows properly.
Thanks for #chintan khetiya & #Robinhood who helped to Solve this.
Related
I have an app that utilizes a TSL 1128 reader to read RFID tags. It uses the IASCIICommandResponder Library to communicate with the reader.
I have one Class called orderFullfill.java that is responsible for the Listview and updating the UI for this class. Th
The Reader functionality is set up in another class (orderResponder.java) that implements this IASCIICommandResponder, so that it can run in the background whilst orderFullfill shows the changes made to the ArrayList.
I have tried passing the Arrayadapter from orderFullfill.java to orderResponder to call notifyDataSetChanged(); but that has no effect. I have to call addPigNumber() method on a button click to update my listview.
Ideally I need the listview to update when a new tag is added to the list. Please can someone help me apply notifyDataSetChanged() in the right place so that when I can a tag it will add to the list automatically. I am very grateful for any help that is received.
public class orderFullfill extends AppCompatActivity implements PopupMenu.OnMenuItemClickListener {int where; public static ArrayList scannedPigs = new ArrayList<String>();
// The Reader currently in use
private Reader mReader = null;
private boolean mIsSelectingReader = false;
// The model that performs actions with the reader
private TriggerModel mModel;
public static String dispatchweek;
public static String customer;
public static String accountnumber;
public static String supplyfarm;
public static String breed;
public static int numberofpigs;
public static int pigNum;
public static ArrayAdapter<String> adapter;
public static String weekNow;
public static Context mContext;
Switch trick; TextView nameholder;
/**
* #return the current AsciiCommander
*/
protected AsciiCommander getCommander()
{
return AsciiCommander.sharedInstance();
}
#Override
protected void onCreate(#Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.orderfullfill);
mContext = orderFullfill.this;
addPigNumber();
InventoryCommand iCommand = InventoryCommand.synchronousCommand();
iCommand.setFilterStrongest(TriState.YES);//high power reading
trick = (Switch) findViewById(R.id.scanM2);
trick.setVisibility(View.INVISIBLE);
trick.setChecked(true);
trick.setText(getResources().getString(R.string.lowPowerScan));
trick.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
#Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
InventoryCommand iCommand = new InventoryCommand();
//InventoryCommand iCommand = InventoryCommand.synchronousCommand();
if(isChecked)
{
iCommand.setTakeNoAction(TriState.YES);
iCommand.setFilterStrongest(TriState.YES);// low power reading
getCommander().executeCommand(iCommand);
trick.setText(getResources().getString(R.string.lowPowerScan));
}
if(!isChecked)
{
trick.setText(getResources().getString(R.string.highPowerScan));
iCommand.setFilterStrongest(TriState.NO);//high power reading
iCommand.setTakeNoAction(TriState.NO);
getCommander().executeCommand(iCommand);
}
}
});
nameholder = (TextView)findViewById(R.id.nameView);
nameholder.setText(customer);
AsciiCommander.createSharedInstance(getApplicationContext());
final AsciiCommander commander = getCommander();
// Ensure that all existing responders are removed
commander.clearResponders();
// Add the LoggerResponder - this simply echoes all lines received from the reader to the log
// and passes the line onto the next responder
// This is ADDED FIRST so that no other responder can consume received lines before they are logged.
// commander.addResponder(new LoggerResponder());// logcat input
// Add responder to enable the synchronous commands
// commander.addSynchronousResponder();
commander.addResponder(new orderResponder());
// Configure the ReaderManager when necessary
ReaderManager.create(getApplicationContext());
// Add observers for changes
ReaderManager.sharedInstance().getReaderList().readerAddedEvent().addObserver(mAddedObserver);
ReaderManager.sharedInstance().getReaderList().readerUpdatedEvent().addObserver(mUpdatedObserver);
ReaderManager.sharedInstance().getReaderList().readerRemovedEvent().addObserver(mRemovedObserver);
// Create a (custom) model and configure its commander and handler
mModel = new TriggerModel();
mModel.setCommander(getCommander());
mModel.initialise();
ListView scroller = (ListView)findViewById(R.id.listviewD);
scroller.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
PopupMenu popup = new PopupMenu(orderFullfill.this, view);
popup.setOnMenuItemClickListener(orderFullfill.this);
popup.inflate(R.menu.edit_menu);
where = position;
popup.show();
}
});
weekNow = orderResponder.getWeeknow();
}
public ArrayAdapter getAdapter()
{
adapter = new ArrayAdapter<>(mContext, android.R.layout.simple_spinner_item, scannedPigs);
return adapter;
}
public void addPigNumber()
{
adapter = new ArrayAdapter<String>(mContext, android.R.layout.simple_spinner_item, scannedPigs);
TextView counter = findViewById(R.id.editTextNumber);
if(numberofpigs >= 0 )
{
counter.setText("Pigs Left: " +numberofpigs);
if(numberofpigs == 0)
{
counter.setBackgroundColor(Color.parseColor("#BCBDF3E8"));
}
}
ListView scroller = findViewById(R.id.listviewD);
try {
adapter.setDropDownViewResource(R.layout.support_simple_spinner_dropdown_item);
scroller.setAdapter(adapter);
}catch (Exception e)
{
String result ="";
result.equals(e.toString());
}
}
public void orderdetailsOnclick(View view) {
addPigNumber();
AlertDialog.Builder alert = new AlertDialog.Builder(this);
alert.setTitle("Customer Order: " + customer);
alert.setMessage("Account Number: " + accountnumber + "\r\n" +
"Dispatch Week: " + dispatchweek + "\r\n" +
"Supply Farm: " + supplyfarm + "\r\n" +
"Breed: "+ breed + "\r\n" + "Number of Pigs: " + pigNum);
alert.setCancelable(true);
alert.show();
}
#Override
public synchronized void onResume()
{
super.onResume();
addPigNumber();
// Register to receive notifications from the AsciiCommander
LocalBroadcastManager.getInstance(this).registerReceiver(mMessageReceiver, new IntentFilter(AsciiCommander.STATE_CHANGED_NOTIFICATION));
// Remember if the pause/resume was caused by ReaderManager - this will be cleared when ReaderManager.onResume() is called
boolean readerManagerDidCauseOnPause = ReaderManager.sharedInstance().didCauseOnPause();
// The ReaderManager needs to know about Activity lifecycle changes
ReaderManager.sharedInstance().onResume();
// The Activity may start with a reader already connected (perhaps by another App)
// Update the ReaderList which will add any unknown reader, firing events appropriately
ReaderManager.sharedInstance().updateList();
// Locate a Reader to use when necessary
AutoSelectReader(!readerManagerDidCauseOnPause);
mIsSelectingReader = false;
displayReaderState();
}
#Override
public synchronized void onPause() {
super.onPause();
// Register to receive notifications from the AsciiCommander
LocalBroadcastManager.getInstance(this).unregisterReceiver(mMessageReceiver);
addPigNumber();
ReaderManager.sharedInstance().onPause();
}
#Override
protected void onDestroy()
{
super.onDestroy();
// Remove observers for changes
ReaderManager.sharedInstance().getReaderList().readerAddedEvent().removeObserver(mAddedObserver);
ReaderManager.sharedInstance().getReaderList().readerUpdatedEvent().removeObserver(mUpdatedObserver);
ReaderManager.sharedInstance().getReaderList().readerRemovedEvent().removeObserver(mRemovedObserver);
// readResponder.tempList = false;
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.reader_menu, menu);
// Reset, connect, disconnect dropdown menu
mResetMenuItem = menu.findItem(R.id.reset_reader_menu_item);
mConnectMenuItem = menu.findItem(R.id.connect_reader_menu_item);
mDisconnectMenuItem= menu.findItem(R.id.disconnect_reader_menu_item);
return true;
}
//----------------------------------------------------------------------------------------------
// ReaderList Observers
//----------------------------------------------------------------------------------------------
Observable.Observer<Reader> mAddedObserver = new Observable.Observer<Reader>()
{
#Override
public void update(Observable<? extends Reader> observable, Reader reader)
{
// See if this newly added Reader should be used
AutoSelectReader(true);
}
};
Observable.Observer<Reader> mUpdatedObserver = new Observable.Observer<Reader>()
{
#Override
public void update(Observable<? extends Reader> observable, Reader reader)
{
}
};
Observable.Observer<Reader> mRemovedObserver = new Observable.Observer<Reader>()
{
#Override
public void update(Observable<? extends Reader> observable, Reader reader)
{
// Was the current Reader removed
if( reader == mReader)
{
mReader = null;
// Stop using the old Reader
getCommander().setReader(mReader);
}
}
};
#Override
public boolean onMenuItemClick(MenuItem item) {
switch (item.getItemId())
{
case R.id.delete_menu:
boolean complete = false;
scannedPigs.remove(where);
numberofpigs = numberofpigs + 1;
//myDB.deleteEntry(scannedItems); -> IF YOU ADD IT TO THE DB REMOVE IT
//select items from the list
addPigNumber();
return true;
case R.id.edit_menu_:
return true;
}
return super.onOptionsItemSelected(item);
}}
orderfullfill.xml
<?xml version="1.0" encoding="utf-8"?><android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<TextView
android:id="#+id/editTextNumber"
android:layout_width="177dp"
android:layout_height="56dp"
android:layout_marginStart="24dp"
android:layout_marginLeft="24dp"
android:layout_marginTop="80dp"
android:textSize="30sp"
app:layout_constraintBottom_toTopOf="#+id/listviewD"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintVertical_bias="1.0" />
<ListView
android:id="#+id/listviewD"
android:layout_width="354dp"
android:layout_height="221dp"
android:layout_marginBottom="12dp"
app:layout_constraintBottom_toTopOf="#+id/scanM2"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.421"
app:layout_constraintStart_toStartOf="parent" />
<Button
android:id="#+id/invoiceMaker"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="12dp"
android:text="#string/makeInvoice"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.75"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="#+id/scanM2" />
<TextView
android:id="#+id/nameView"
android:layout_width="333dp"
android:layout_height="52dp"
android:layout_marginLeft="25dp"
android:layout_marginTop="16dp"
android:layout_marginRight="25dp"
android:layout_marginBottom="303dp"
android:textSize="20dp"
app:layout_constraintBottom_toTopOf="#+id/scanM2"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.0"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintVertical_bias="0.0" />
<Button
android:id="#+id/orderdetailsBtn"
android:layout_width="119dp"
android:layout_height="54dp"
android:layout_marginTop="68dp"
android:layout_marginEnd="20dp"
android:layout_marginRight="20dp"
android:onClick="orderdetailsOnclick"
android:text="#string/showOrder"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.887"
app:layout_constraintStart_toEndOf="#+id/editTextNumber"
app:layout_constraintTop_toTopOf="parent" />
<Switch
android:id="#+id/scanM2"
android:layout_width="359dp"
android:layout_height="39dp"
android:layout_below="#id/listviewD"
android:layout_marginTop="232dp"
android:text="#string/highPowerScan"
android:textOff="No"
android:textOn="Yes"
android:textSize="27dp"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.461"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="#+id/orderdetailsBtn" />/android.support.constraint.ConstraintLayout>
orderResponder.java -> this is the class that the TSL reader communicates with via ASCII when reading RFID tags. The method Splicer adds the RFID values to the ArrayAdapter then notifyDataSetChanged(); is called. However nothing happens when this method is called from outside orderFullfill.class.
public class orderResponder extends Application implements IAsciiCommandResponder {
public static boolean tempList;
NoteHelper myDB;
public List<String> getReadInput() {
return readInput;
}
public void setReadInput(List<String> readInput) {
this.readInput = readInput;
}
public static List<String> readInput = new ArrayList<>();
#Override
public boolean isResponseFinished() {
return false;
}
#Override
public void clearLastResponse() {
}
#Override
public boolean processReceivedLine(String s, boolean b) throws Exception {
isitMe(s);
return false;
}
public List<String> getList()
{
return readInput;
}
public boolean isitMe (String input)
{
String firstFourChars = "";
//get first 4 chars to see if it contains "EP: "
if(input.length()>4)
{
firstFourChars = input.substring(0,4);
}
else
{
firstFourChars = input;
}
if(firstFourChars.equals("EP: "))// this is the inital identifier for the RFID tags
{
splicer(input);
return true;
}
else
{
return false;
}
}
//takes the last 24 characters removing the 'EP: '
public void splicer (String input)
{ // ArrayAdapter magic = orderFullfill.getAdapter(); THIS Didnt work
orderFullfill.adapter = new ArrayAdapter<String>(orderFullfill.mContext, android.R.layout.simple_spinner_item, orderFullfill.scannedPigs);
String output ="";
output = input.substring(input.length() -24);//maybe take 24 chars
if (orderFullfill.scannedPigs.size() == 0) {
// orderFullfill.scannedPigs.add(output);
orderFullfill.adapter.add(output);
orderFullfill.adapter.notifyDataSetChanged();
orderFullfill.numberofpigs = orderFullfill.numberofpigs - 1;
} else//if the list has values check you are not duplicating the values
{
if (orderFullfill.scannedPigs.contains(output)) {
return;//you are already in the list
} else//you are unique you can join the list
{
// orderFullfill.scannedPigs.add(output);
orderFullfill.adapter.add(output);
orderFullfill.adapter.notifyDataSetChanged();
orderFullfill.numberofpigs = orderFullfill.numberofpigs - 1;
}
}
}
public static String getWeeknow()
{
Date date = new Date();
SimpleDateFormat formatter = new SimpleDateFormat("dd/MM/yyyy");
String dateH = formatter.format(date);
//String dateH = date.toString();
String[] array = dateH.split("\\/");
String output ="";
int month = Integer.parseInt(array[1]);
month = month -1;
Calendar calendar = Calendar.getInstance();
calendar.set(Integer.parseInt(array[2]),month,Integer.parseInt(array[0]));
int weekOfyear = calendar.get(Calendar.WEEK_OF_YEAR);
output = String.valueOf(weekOfyear);
return output;
}}
create orderResponder constructor method. and send your activity(orderFullfill.this) and context to orderResponder as parameter. call like this;
((orderFullfill)activity).adapter = new ArrayAdapter<String>(context, android.R.layout.simple_spinner_item, ((orderFullfill)activity).scannedPigs);
((orderFullfill)activity).adapter.notifyDataSetChanged();
i hope it works.
I am completely new to android development and I'm trying to create an OCR app. Now my problem is I want to get the progress during the process of ocr.
And I found a blog post of rmtheis about this but I don't know how to implement it to my project.
Here is the code to his blog:
The progress percentage can be used in a thermometer-style ProgressBar. The bounding boxes can be drawn on top of the display of the input image during recognition.
Implementing this callback requires using an alternate constructor for the TessBaseAPI object and implementation of the ProgressNotifier interface:
ProgressBar progressBar = (ProgressBar) findViewById(R.id.progressBar1);
// Create the TessBaseAPI object, and register to receive OCR progress updates
TessBaseAPI baseApi = new TessBaseAPI(this);
baseApi.getHOCRText(myImage);
#Override
public void onProgressValues(ProgressValues progressValues) {
progressBar.setProgress(progressValues.getPercent());}
Here is my code for in TessBaseOCR.java
public class TessOCR{
private TessBaseAPI mTess;
public TessOCR(String language){
// TODO Auto-generated constructor stub
mTess = new TessBaseAPI();
// AssetManager assetManager=
String datapath = Environment.getExternalStorageDirectory() + "/ImageToText/";
// AssetManager assetManager = getAssets();
File dir = new File(datapath + "/tessdata/");
if (!dir.exists())
dir.mkdirs();
mTess.init(datapath, language);
}
public String getOCRResult(Bitmap bitmap) {
mTess.setImage(bitmap);
String result = mTess.getUTF8Text();
return result;
// TessBaseAPI baseApi = new TessBaseAPI();
//baseApi.getUTF8Text();
}
public void onDestroy() {
if (mTess != null)
mTess.stop();
}
}
In my CropActivity.Java:
public class CropActivity extends AppCompatActivity implements
TessBaseAPI.ProgressNotifier{
ProgressBar progressBar;
#Override
protected void onCreate( Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//my codes here
}
//Some codes here
//my Scan button
public void onScanClick(View view) {
try {
BitmapDrawable drawable = (BitmapDrawable) imgView.getDrawable();
Bitmap bitmap = drawable.getBitmap();
//mImage.setImageBitmap(converted);
doOCR(convertColorIntoBlackAndWhiteImage(bitmap) );
}catch (Exception e) {
Toast.makeText(this,"Please Load an image first!",
Toast.LENGTH_LONG).show();
}
}
public void ocrprogressbar() {
I use layout inflater that will popup when scan button is pressed and from there I have my progressBar that I want get the progress update of Ocr
LayoutInflater li = getLayoutInflater();
final View promptsView = li.inflate(R.layout.ocr_progress, null);
AlertDialog.Builder alertDialogBuilder = new AlertDialog.Builder(
context);
progressBar = (ProgressBar)findViewById(R.id.progressBar2);
TextView txt = (TextView)findViewById(R.id.txtprcnt);
// set prompts.xml to alertdialog builder
alertDialogBuilder.setView(promptsView);
alertDialogBuilder
.setCancelable(false)
.setPositiveButton("Stop",
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog,int id)
{
mTessOCR.onDestroy();
}
});
// create alert dialog
AlertDialog alertDialog = alertDialogBuilder.create();
// show it
alertDialog.show();
// set prompts.xml to alertdialog build
}
public void doOCR(final Bitmap bitmap) {
ocrprogressbar();
new Thread(new Runnable() {
public void run() {
final String result = mTessOCR.getOCRResult(bitmap).toString();
runOnUiThread(new Runnable() {
#Override
public void run() {
// TODO Auto-generated method stub
if (result != null && !result.equals("")) {
String s = result.trim();
textView.setText(result);
finalresult = textView.getText().toString();
startActivityOnOCRresult();
}
//mProgressDialog.dismiss();
}
});
};
}
)
.start();
}
//My override method as what mentioned in the blog post
#Override
public void onProgressValues (TessBaseAPI.ProgressValues progressValues){
progressBar.setProgress(progressValues.getPercent());
}
}
My ocr_progress.xml layout that will be inflated
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical" android:layout_width="match_parent"
android:layout_height="match_parent">
<ProgressBar
android:id="#+id/progressBar2"
style="?android:attr/progressBarStyleHorizontal"
android:layout_width="match_parent"
android:layout_height="50dp"
android:layout_below="#+id/textView2"
android:layout_centerHorizontal="true"
android:layout_marginLeft="10dp"
android:layout_marginRight="10dp"
android:layout_marginTop="20dp"
android:indeterminateOnly="false"
android:max="100"
android:progressTint="#color/colorAccent" />
<TextView
android:id="#+id/textView2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="40dp"
android:textSize="25sp"
android:textColor="#color/colorPrimaryDark"
android:text="Processing..."
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true" />
</RelativeLayout>
My progressbar pops up but It's stucked and not getting progress. I am not sure if I'm doing it correctly. Please help me
I need to introduce data in an EditText but i want to use an virtual keyboard, not the android keyboard. If I use setKeyListener(null) the cursor is invisible even after using setCursorVisible(true).
Is it possible to make an EditText where even if it isn't editable the cursor is visible ?
EDIT 2 :
I found an partial method to do that, but it's not working when i'm double taping the EditText.
I made an setOnClickListner() and an setOnLongClickListner() method for the EditText. In this methods I hide the Soft Input from the Window, also i use setTextIsSelectable(false). My only problem is that when I double tap the EditText the soft input keyboard shows and I dont know how to hide it, I tried to use android:windowSoftInputMode="stateAlwaysHidden" in manifest, but it doesn't work either.
EDIT :
Here is the code that I'm using at this moment for my base converter calculator.
public class MainActivity extends AppCompatActivity {
EditText number;
EditText base;
boolean baseB = false;
String numberS = "0";
String baseS = "10";
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(activity_main);
//make the EditText for number and base not editable
number = (EditText) findViewById(R.id.number);
number.setKeyListener(null);
base = (EditText) findViewById(R.id.base);
base.setKeyListener(null);
//... more code here (changing fonts for each EditText and changing status bar color
}
// I have a function for each button all are the same
public void onClickBaseChange(View v) {
if (baseB) {
baseB = false;
// i use toasts at this moment to know when i'm on number or base field
Toast.makeText(this, "Number", Toast.LENGTH_SHORT).show();
} else {
baseB = true;
Toast.makeText(this, "Base", Toast.LENGTH_SHORT).show();
}
}
public void onClickB0(View v) {
if (numberS.length() > 0 && !numberS.equals("0") && !baseB) {
numberS += "0";
number = (EditText) findViewById(R.id.number);
number.setText(numberS, TextView.BufferType.EDITABLE);
number.setSelection(numberS.length());
} else {
if (Integer.valueOf(baseS) >= 1) {
baseS += "0";
base = (EditText) findViewById(R.id.base);
base.setText(baseS, TextView.BufferType.EDITABLE);
}
}
}
public void onClickB1(View v) {
if (numberS.equals("0")) {
numberS = "1";
} else {
numberS += "1";
}
number = (EditText) findViewById(R.id.number);
number.setText(numberS, TextView.BufferType.EDITABLE);
number.requestFocus();
number.setSelection(numberS.length());
}
And the xml looks like this :
<android.widget.RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:background="#color/colorBackground"
tools:context="manastur.calculator.MainActivity">
<EditText
android:id="#+id/base"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_marginRight="20dp"
android:layout_marginTop="120dp"
android:background="#android:color/transparent"
android:cursorVisible="true"
android:text=""
android:textColor="#color/text"
android:textSize="30dp" />
<EditText
android:id="#+id/number"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:layout_marginLeft="30dp"
android:layout_marginTop="50dp"
android:background="#android:color/transparent"
android:cursorVisible="true"
android:text=""
android:textColor="#color/text"
android:textSize="50dp" />
<LinearLayout
android:id="#+id/secondRow"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_above="#+id/firstRow"
android:layout_centerHorizontal="true">
<Button
android:id="#+id/b1"
android:layout_width="85dp"
android:layout_height="85dp"
android:background="#drawable/b1"
android:onClick="onClickB1" />
<Button
android:id="#+id/b2"
android:layout_width="85dp"
android:layout_height="85dp"
android:background="#drawable/b2"
android:onClick="onClickB2" />
<!-- from this point on is the same, there are 5 LinearLayouts which
represents the 5 rows of button of the num pad -->
Use this code to achieve that,
While develop I took reference from native Dialpad code
KeypadlessKeypad.java
import android.content.Context;
import android.graphics.Rect;
import android.support.v4.view.MotionEventCompat;
import android.text.InputType;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.View;
import android.view.accessibility.AccessibilityEvent;
import android.view.inputmethod.InputMethodManager;
import android.widget.EditText;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
public class KeypadlessKeypad extends EditText {
private static final Method mShowSoftInputOnFocus = getSetShowSoftInputOnFocusMethod(
EditText.class, "setShowSoftInputOnFocus", boolean.class);
public static Method getSetShowSoftInputOnFocusMethod(Class<?> cls, String methodName, Class<?>... parametersType) {
Class<?> sCls = cls.getSuperclass();
while (sCls != Object.class) {
try {
return sCls.getDeclaredMethod(methodName, parametersType);
} catch (NoSuchMethodException e) {
// Just super it again
}
sCls = sCls.getSuperclass();
}
return null;
}
private Context mContext;
/**
* Listener for Copy, Cut and Paste event
* Currently callback only for Paste event is implemented
*/
private OnEditTextActionListener mOnEditTextActionListener;
public KeypadlessKeypad(Context context) {
super(context);
mContext = context;
init();
}
public KeypadlessKeypad(Context context, AttributeSet attrs) {
super(context, attrs);
mContext = context;
init();
}
public KeypadlessKeypad(Context context, AttributeSet attrs,
int defStyle) {
super(context, attrs, defStyle);
mContext = context;
init();
}
#Override
protected void onSelectionChanged(int selStart, int selEnd) {
super.onSelectionChanged(selStart, selEnd);
}
public final void appendText(CharSequence text) {
append(text, 0, text.length());
}
/***
* Initialize all the necessary components of TextView.
*/
private void init() {
setSingleLine(true);
synchronized (this) {
setInputType(getInputType() | InputType.TYPE_TEXT_FLAG_NO_SUGGESTIONS);
setFocusableInTouchMode(true);
}
reflexSetShowSoftInputOnFocus(false); // Workaround.
// Ensure that cursor is at the end of the input box when initialized. Without this, the
// cursor may be at index 0 when there is text added via layout XML.
setSelection(getText().length());
}
#Override
protected void onFocusChanged(boolean focused, int direction, Rect previouslyFocusedRect) {
super.onFocusChanged(focused, direction, previouslyFocusedRect);
hideKeyboard();
}
#Override
public boolean onTouchEvent(MotionEvent event) {
final boolean ret = super.onTouchEvent(event);
// Must be done after super.onTouchEvent()
hideKeyboard();
return ret;
}
private void hideKeyboard() {
final InputMethodManager imm = ((InputMethodManager) getContext()
.getSystemService(Context.INPUT_METHOD_SERVICE));
if (imm != null && imm.isActive(this)) {
imm.hideSoftInputFromWindow(getApplicationWindowToken(), 0);
}
}
private void reflexSetShowSoftInputOnFocus(boolean show) {
if (mShowSoftInputOnFocus != null) {
invokeMethod(mShowSoftInputOnFocus, this, show);
} else {
// Use fallback method. Not tested.
hideKeyboard();
}
}
public static Object invokeMethod(Method method, Object receiver, Object... args) {
try {
return method.invoke(receiver, args);
} catch (IllegalArgumentException e) {
} catch (IllegalAccessException e) {
} catch (InvocationTargetException e) {
}
return null;
}
#Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
super.onMeasure(widthMeasureSpec, heightMeasureSpec);
int textViewWidth = View.MeasureSpec.getSize(widthMeasureSpec);
int height = getMeasuredHeight();
this.setMeasuredDimension(textViewWidth, height);
}
#Override
protected void onTextChanged(CharSequence text, int start, int before,
int after) {
super.onTextChanged(text, start, before, after);
}
#Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
}
#Override
public boolean onTextContextMenuItem(int id) {
boolean consumed = super.onTextContextMenuItem(id);
switch (id) {
case android.R.id.paste:
if (mOnEditTextActionListener != null) {
mOnEditTextActionListener.onPaste();
}
break;
}
return consumed;
}
/**
* Setter method for {#link #mOnEditTextActionListener}
*
* #param onEditTextActionListener
* Instance of the {#link OnEditTextActionListener}
*/
public void setOnEditTextActionListener(OnEditTextActionListener onEditTextActionListener) {
this.mOnEditTextActionListener = onEditTextActionListener;
}
private Rect mRect = new Rect();
#Override
public boolean dispatchTouchEvent(MotionEvent event) {
final int action = MotionEventCompat.getActionMasked(event);
int[] location = new int[2];
getLocationOnScreen(location);
mRect.left = location[0];
mRect.top = location[1];
mRect.right = location[0] + getWidth();
mRect.bottom = location[1] + getHeight();
int x = (int) event.getX();
int y = (int) event.getY();
if (action == MotionEvent.ACTION_DOWN && !mRect.contains(x, y)) {
InputMethodManager input = (InputMethodManager) mContext.getSystemService(Context.INPUT_METHOD_SERVICE);
input.hideSoftInputFromWindow(getWindowToken(), 0);
}
return super.dispatchTouchEvent(event);
}
#Override
public void sendAccessibilityEventUnchecked(AccessibilityEvent event) {
if (event.getEventType() == AccessibilityEvent.TYPE_VIEW_TEXT_CHANGED) {
// Since we're replacing the text every time we add or remove a
// character, only read the difference. (issue 5337550)
final int added = event.getAddedCount();
final int removed = event.getRemovedCount();
final int length = event.getBeforeText().length();
if (added > removed) {
event.setRemovedCount(0);
event.setAddedCount(1);
event.setFromIndex(length);
} else if (removed > added) {
event.setRemovedCount(1);
event.setAddedCount(0);
event.setFromIndex(length - 1);
} else {
return;
}
} else if (event.getEventType() == AccessibilityEvent.TYPE_VIEW_FOCUSED) {
// The parent EditText class lets tts read "edit box" when this View has a focus, which
// confuses users on app launch (issue 5275935).
return;
}
super.sendAccessibilityEventUnchecked(event);
}
/**
* Interface to get callback from the Edittext copy, cut and paste event
* For time being only the Paste Event callback is generated
*/
public interface OnEditTextActionListener {
/**
* If Edittext get paste event then this method will be called
*/
void onPaste();
}
}
In your xml you can give like this,
<[package name].KeypadlessKeypad
android:id="#+id/dialnumbertv"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#00000000"
android:cursorVisible="false"
android:ellipsize="start"
android:gravity="center"
android:inputType="phone"
android:singleLine="true"
android:textIsSelectable="true"
android:textSize="30sp"
android:textStyle="italic"
android:visibility="visible"/>
And in your fragment you can implement like this,
public void onViewCreated(final View view, Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
mDialNumbertv = view.findViewById(R.id.dialnumbertv);
mDialNumbertv.setCursorVisible(false);
mDialNumbertv.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if (!isDigitsEmpty()) {
mDialNumbertv.setCursorVisible(true);
}
}
});
mDialNumbertv.addTextChangedListener(new TextWatcher() {
#Override
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
#Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
}
#Override
public void afterTextChanged(Editable s) {
if (isDigitsEmpty()) {
mDialNumbertv.setCursorVisible(false);
}
// updateDeleteButton();
}
});
mDialNumbertv.setOnLongClickListener(new View.OnLongClickListener() {
#Override
public boolean onLongClick(View v) {
// Ref https://android.googlesource.com/platform/packages/apps/Contacts/+/39948dc7e34dc2041b801058dada28fedb80c388/src/com/android/contacts/dialpad/DialpadFragment.java
// Right now EditText does not show the "paste" option when cursor is not visible.
// To show that, make the cursor visible, and return false, letting the EditText
// show the option by itself.
mDialNumbertv.setCursorVisible(true);
return false;
}
});
mDialNumbertv.setOnEditTextActionListener(
new KeypadlessKeypad.OnEditTextActionListener() {
#Override
public void onPaste() {
// If some content pasted on mDialNumbertv
// we need to run some search on Contact and Price
String mobileNumber = mDialNumbertv.getText().toString();
if (TextUtils.isEmpty(mobileNumber)) {
return;
}
// updateContactName(mobileNumber);
}
});
}
private KeypadlessKeypad mDialNumbertv;
private boolean isDigitsEmpty() {
return mDialNumbertv.length() == 0;
}
private void setClickedDigit(final String digitToSet) {
if (!TextUtils.isEmpty(digitToSet)) {
char digit = digitToSet.charAt(0);
String mobileNumber = mDialNumbertv.getText() + digitToSet;
mDialNumbertv.getText().insert(mDialNumbertv.getSelectionStart(), digitToSet);
// If the cursor is at the end of the text we hide it.
final int length = mDialNumbertv.length();
if (length == mDialNumbertv.getSelectionStart() && length == mDialNumbertv.getSelectionEnd()) {
mDialNumbertv.setCursorVisible(false);
}
}
}
I wanted the same behavior which I achieved as follows -
Make a custom class that will override 2 methods of AppCompatEditText.
class CustomEditText(context: Context?, attrs: AttributeSet) : AppCompatEditText(context, attrs) {
override fun onCheckIsTextEditor(): Boolean {
return true
}
override fun isTextSelectable(): Boolean {
return true
}
}
In the XML file, create EditText using this custom view.
<com.ui.custom.CustomEditText
android:id="#+id/et_email"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:inputType="none"
android:focusable="true"
android:gravity="center"
android:focusableInTouchMode="true"/>
Now, just add onFocusChangeListener and set editText.setKeyListener = null.
binding.etEmail.onFocusChangeListener = OnFocusChangeListener { v, hasFocus ->
if (hasFocus) {
binding.etEmail.keyListener = null
}
}
You can add the same on onTouch if that is the requirement.
The main issue here is that onCheckIsTextEditor() of View class always returns false, which leads to cursor never blinking or being visible even if setCursorVisible(true) was called in code.
I hope it helps.
You can use edittext.setselection(0)
or
maybe you can request focus using requestfocus()
I'm writing a calculator app for android using android studio. I want to used 4 buttons for inputting values and functions. However the way I am currently doing it takes the input from the text written on the button. So for my button 1/2/3 when this is pressed 1/2/3 is passed to the textView.
Below is my MainActivity:
package com.example.myfirstapp;
import android.media.MediaPlayer;
import android.support.v7.app.ActionBarActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.MediaController;
import android.widget.TextView;
public class MainActivity extends ActionBarActivity {
private int[] operatorButtons = {R.id.operators};
private int[] numericButtons = {R.id.onetwothree, R.id.fourfivesix, R.id.seveneightninezero};
private boolean lastNumeric, stateError;
private TextView txtScreen;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// Find the TextView
this.txtScreen = (TextView) findViewById(R.id.txtScreen);
// Find and set OnClickListener to numeric buttons
setNumericOnClickListener();
// Find and set OnClickListener to operator buttons, equal button and decimal point button
setOperatorOnClickListener();
}
private void setNumericOnClickListener() {
// Create a common OnClickListener
View.OnClickListener listener = new View.OnClickListener() {
#Override
public void onClick(View v) {
// Just append/set the text of clicked button
Button button = (Button) v;
if (stateError) {
// If current state is Error, replace the error message
txtScreen.setText(button.getText());
stateError = false;
} else {
// If not, already there is a valid expression so append to it
txtScreen.append(button.getText());
}
// Set the flag
lastNumeric = true;
}
};
// Assign the listener to all the numeric buttons
for (int id : numericButtons) {
findViewById(id).setOnClickListener(listener);
}
}
private void setOperatorOnClickListener() {
// Create a common OnClickListener for operators
View.OnClickListener listener = new View.OnClickListener() {
#Override
public void onClick(View v) {
// If the current state is Error do not append the operator
// If the last input is number only, append the operator
if (lastNumeric && !stateError) {
Button button = (Button) v;
txtScreen.append(button.getText());
lastNumeric = false;
}
}
};
// Assign the listener to all the operator buttons
for (int id : operatorButtons) {
findViewById(id).setOnClickListener(listener);
}
// Equal button
/*findViewById(R.id.btnEqual).setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
onEqual();
}
});*/
}
}
and my activity_main:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:id="#+id/txtScreen"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true"
android:gravity="right|center_vertical"
android:maxLength="16"
android:padding="10dp"
android:textAppearance="?android:attr/textAppearanceLarge"
android:textSize="30sp"
android:typeface="serif" />
<!--<Button-->
<!--android:id="#+id/equal1"-->
<!--android:layout_width="match_parent"-->
<!--android:layout_height="100dp"-->
<!--android:text="="-->
<!--/>-->
<Button
android:id="#+id/equal2"
android:layout_width="match_parent"
android:layout_height="100dp"
android:text="="
android:layout_alignParentBottom="true"
/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_below="#id/txtScreen"
android:orientation="vertical"
android:layout_above="#id/equal2">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1">
<Button
android:id="#+id/onetwothree"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1"
android:text="1/2/3"/>
<Button
android:id="#+id/fourfivesix"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1"
android:text="4/5/6"/>
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1">
<Button
android:id="#+id/seveneightninezero"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1"
android:text="7/8/9/0"/>
<Button
android:id="#+id/operators"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1"
android:text="+-*/"/>
</LinearLayout>
</LinearLayout>
</RelativeLayout>
Will it be possible for me to get the input of 1, 2 or 3 from my first button for example? So on 1 press you get 1, 2 press gives 2 etc.
Any suggestions/ ideas on how I can move forward with this are greatly appreciated.
Kind Regards,
Ben
You could use a timer or delay variable to detect single, double or triple taps. This post may be of interest. If the time interval is not a factor, you could just keep track of the last pressed button and if the same button is being pressed again, update the text accordingly.
If you follow approach one, the code for the click listener for button onetwothree may be something like this (I commented out setNumericOnClickListener() and setOperatorOnClickListener(); in mainActivity onCreate and added the following):
Button onetwothree = (Button) findViewById(R.id.onetwothree);
onetwothree.setOnTouchListener(new View.OnTouchListener() {
Handler handler = new Handler();
int numberOfTaps = 0;
long lastTapTimeMs = 0;
long touchDownMs = 0;
#Override
public boolean onTouch(View v, MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
touchDownMs = System.currentTimeMillis();
break;
case MotionEvent.ACTION_UP:
handler.removeCallbacksAndMessages(null);
if ((System.currentTimeMillis() - touchDownMs) > ViewConfiguration.getTapTimeout()) {
//it was not a tap
numberOfTaps = 0;
lastTapTimeMs = 0;
break;
}
if (numberOfTaps > 0
&& (System.currentTimeMillis() - lastTapTimeMs) < ViewConfiguration.getDoubleTapTimeout()) {
numberOfTaps += 1;
} else {
numberOfTaps = 1;
}
lastTapTimeMs = System.currentTimeMillis();
if (numberOfTaps == 1) {
handler.postDelayed(new Runnable() {
#Override
public void run() {
if (txtScreen.getText().toString() == "") {
txtScreen.setText("1");
} else txtScreen.append("1");
}
}, ViewConfiguration.getDoubleTapTimeout());
}else if (numberOfTaps == 2) {
handler.postDelayed(new Runnable() {
#Override
public void run() {
if (txtScreen.getText().toString() == "") {
txtScreen.setText("2");
} else txtScreen.append("2");
}
}, ViewConfiguration.getDoubleTapTimeout());
} else if (numberOfTaps == 3) {
if (txtScreen.getText().toString() == "") {
txtScreen.setText("3");
} else txtScreen.append("3");
}
}
return true;
}
});
Complete MainActivity:
package com.example.myfirstapp;
import android.os.Bundle;
import android.os.Handler;
import android.support.v7.app.ActionBarActivity;
import android.view.MotionEvent;
import android.view.View;
import android.view.ViewConfiguration;
import android.widget.Button;
import android.widget.TextView;
public class MainActivity extends ActionBarActivity {
private int[] operatorButtons = {R.id.operators};
private int[] numericButtons = {R.id.onetwothree, R.id.fourfivesix, R.id.seveneightninezero};
private boolean lastNumeric, stateError;
private TextView txtScreen;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// Find the TextView
this.txtScreen = (TextView) findViewById(R.id.txtScreen);
// Find and set OnClickListener to numeric buttons
// setNumericOnClickListener();
// Find and set OnClickListener to operator buttons, equal button and decimal point button
// setOperatorOnClickListener();
Button onetwothree = (Button) findViewById(R.id.onetwothree);
onetwothree.setOnTouchListener(new View.OnTouchListener() {
Handler handler = new Handler();
int numberOfTaps = 0;
long lastTapTimeMs = 0;
long touchDownMs = 0;
#Override
public boolean onTouch(View v, MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
touchDownMs = System.currentTimeMillis();
break;
case MotionEvent.ACTION_UP:
handler.removeCallbacksAndMessages(null);
if ((System.currentTimeMillis() - touchDownMs) > ViewConfiguration.getTapTimeout()) {
//it was not a tap
numberOfTaps = 0;
lastTapTimeMs = 0;
break;
}
if (numberOfTaps > 0
&& (System.currentTimeMillis() - lastTapTimeMs) < ViewConfiguration.getDoubleTapTimeout()) {
numberOfTaps += 1;
} else {
numberOfTaps = 1;
}
lastTapTimeMs = System.currentTimeMillis();
if (numberOfTaps == 1) {
handler.postDelayed(new Runnable() {
#Override
public void run() {
if (txtScreen.getText().toString() == "") {
txtScreen.setText("1");
} else txtScreen.append("1");
}
}, ViewConfiguration.getDoubleTapTimeout());
}else if (numberOfTaps == 2) {
handler.postDelayed(new Runnable() {
#Override
public void run() {
if (txtScreen.getText().toString() == "") {
txtScreen.setText("2");
} else txtScreen.append("2");
}
}, ViewConfiguration.getDoubleTapTimeout());
} else if (numberOfTaps == 3) {
if (txtScreen.getText().toString() == "") {
txtScreen.setText("3");
} else txtScreen.append("3");
}
}
return false;
}
});
}
private void setNumericOnClickListener() {
// Create a common OnClickListener
View.OnClickListener listener = new View.OnClickListener() {
#Override
public void onClick(View v) {
// Just append/set the text of clicked button
Button button = (Button) v;
if (stateError) {
// If current state is Error, replace the error message
txtScreen.setText(button.getText());
stateError = false;
} else {
// If not, already there is a valid expression so append to it
txtScreen.append(button.getText());
}
// Set the flag
lastNumeric = true;
}
};
// Assign the listener to all the numeric buttons
for (int id : numericButtons) {
findViewById(id).setOnClickListener(listener);
}
}
private void setOperatorOnClickListener() {
// Create a common OnClickListener for operators
View.OnClickListener listener = new View.OnClickListener() {
#Override
public void onClick(View v) {
// If the current state is Error do not append the operator
// If the last input is number only, append the operator
if (lastNumeric && !stateError) {
Button button = (Button) v;
txtScreen.append(button.getText());
lastNumeric = false;
}
}
};
// Assign the listener to all the operator buttons
for (int id : operatorButtons) {
findViewById(id).setOnClickListener(listener);
}
}
}
You can take all numbers when doing some operation
(Button) plusBtn = (Button) findViewById(R.id.plusBtn);
plusBtn.setOnClickListener(new OnClickListener(){
#Override
public voidonClick(View v){
number1 = Integer.parseInt(txtScreen.getText().toString());
});
Where number1 is global int. But I don't know how it can help you and if it is a good approach. You could find a better solution, just remember how to parse the String from your TextView to Integer for your calculation.
I am having this problem where I want to fix the position of my layout. I want to fix it in the center of my layout but every time I click on EditText which makes a keyboard pop up, the TextView shifts up and I don't want that to happen. Here is my code:
comment.xml:
<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout
xmlns:flatui="http://schemas.android.com/apk/res-auto"
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:fresco="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent" android:fitsSystemWindows="true"
android:id="#+id/comments_coordinator_layout">
<android.support.design.widget.AppBarLayout
android:layout_height="wrap_content"
android:layout_width="match_parent"
android:theme="#style/AppTheme.AppBarOverlay">
<android.support.v7.widget.Toolbar
android:id="#+id/comments_appbar"
android:layout_width="match_parent"
android:layout_height="?attr/actionBarSize"
android:background="?attr/colorPrimary"
app:popupTheme="#style/AppTheme.PopupOverlay" />
</android.support.design.widget.AppBarLayout>
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/layout_comments">
<LinearLayout
android:id="#+id/send_message"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:padding="4dp"
android:layout_alignParentBottom="true"
android:orientation="horizontal" >
<com.cengalabs.flatui.views.FlatEditText
android:fontFamily="sans-serif"
android:id="#+id/write_comment"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="5"
android:paddingTop="6dp"
android:paddingBottom="6dp"
android:paddingLeft="5dp"
android:paddingRight="5dp"
android:gravity="left"
android:textSize="16sp"
flatui:fl_theme="#array/color_primary_theme"
android:textColor="#000000"
android:cursorVisible="false"
android:hint="Comment back!"
android:background="#color/feed_bg"
android:inputType="textMultiLine"
flatui:fl_fieldStyle="fl_box"
android:scrollHorizontally="false" />
<com.cengalabs.flatui.views.FlatButton
android:fontFamily="sans-serif"
android:id="#+id/send_comment"
android:layout_width="wrap_content"
android:layout_height="fill_parent"
android:layout_marginLeft="5dp"
android:textSize="16sp"
android:padding="5dp"
android:layout_gravity="center_vertical|center_horizontal"
android:text="Send"
flatui:fl_theme="#array/color_primary_theme"
android:textAllCaps="false"
flatui:fl_textAppearance="fl_light"/>
</LinearLayout>
<android.support.v7.widget.RecyclerView
android:scrollbars="vertical"
app:layout_behavior="#string/appbar_scrolling_view_behavior"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_above="#id/send_message"
android:id="#+id/view_comments">
</android.support.v7.widget.RecyclerView>
<TextView
android:id="#+id/no_comments_text"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center_horizontal|center_vertical"
android:visibility="gone"
android:textSize="16sp"
android:fontFamily="sans-serif"
android:text="No comments to display." />
</RelativeLayout>
</android.support.design.widget.CoordinatorLayout>
Comments.java:
public class Comments extends AppCompatActivity {
Post post;
private CommentsDataSource commentsDatasource;
//Local Database for storing posts
private PostsDataSource postsDataSource;
private FireBaseApplication application;
private List<Comment> commentItems;
private CommentsRecyclerViewAdapter commentsRecyclerViewAdapter;
private RecyclerView commentsView;
private TextView noCommentsView;
private Toolbar toolbar;
private LinearLayoutManager llm;
private NotificationManager notificationManager;
private boolean isNotificationActive;
private String postId;
private String tab;
private String userId;
private String posterUserId;
private String posterName;
private String postTimeStamp;
private String postStatus;
//Progress overlay
View progressOverlay;
DatabaseQuery databaseQuery;
String name;
private Firebase firebaseRef = new Firebase("https://tabsapp.firebaseio.com/");
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.comments);
setupActionBar();
setupActivity(savedInstanceState);
final EditText comment = (EditText) findViewById(R.id.write_comment);
getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE);
getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);
//Once we send the post, we want to
comment.setOnEditorActionListener(new TextView.OnEditorActionListener() {
#Override
public boolean onEditorAction(TextView v, int actionId,
KeyEvent event) {
comment.setCursorVisible(false);
if (event != null && (event.getKeyCode() == KeyEvent.KEYCODE_ENTER)) {
InputMethodManager in = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
comment.setImeOptions(EditorInfo.IME_ACTION_DONE);
in.hideSoftInputFromWindow(comment.getApplicationWindowToken(), InputMethodManager.HIDE_NOT_ALWAYS);
}
return false;
}
});
//Hide the cursor until view is clicked on
View.OnTouchListener onTouchListener = new View.OnTouchListener(){
#Override
public boolean onTouch(View v, MotionEvent event) {
System.out.println("Touched");
if (v.getId() == comment.getId()) {
comment.setCursorVisible(true);
}
commentsView.postDelayed(new Runnable() {
#Override
public void run() {
commentsView.smoothScrollToPosition(commentsView.getAdapter().getItemCount() - 1);
}
}, 250);
return false;
}
};
comment.setOnTouchListener(onTouchListener);
//Button for sending post
final Button button = (Button) findViewById(R.id.send_comment);
button.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
if (TextUtils.isEmpty(comment.getText())) {
Toast.makeText(Comments.this, "Please enter in a comment first.", Toast.LENGTH_SHORT).show();
} else {
String text = comment.getText().toString();
Comment createdComment = new Comment("", postId, name, text, userId, getDateTime());
Toast.makeText(Comments.this, "Successfully commented.", Toast.LENGTH_SHORT).show();
comment.setText("");
InputMethodManager in = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
in.hideSoftInputFromWindow(comment.getApplicationWindowToken(), InputMethodManager.HIDE_NOT_ALWAYS);
comment.setCursorVisible(false);
updatePost();
databaseQuery.saveCommentToFirebase(createdComment);
saveCommentInCloud(createdComment, tab);
if (noCommentsView.getVisibility() == View.VISIBLE) {
noCommentsView.setVisibility(View.GONE);
}
//Notify friends that user has posted a comment on their post. Don't get notification if you posted on your own post.
// if(!createdComment.getCommenterUserId().equals(userId)) {
// showNotification(v, commenter);
// }
}
}
});
//Now we have to show a loading bar so that we are loading the comments. While we are loading the comments, we update the comments header
populateCommentView(postId);
}
public void populateCommentView(String postId) {
commentItems = new ArrayList<Comment>();
getComments(postId);
}
private void setupActionBar() {
toolbar = (Toolbar) findViewById(R.id.comments_appbar);
setSupportActionBar(toolbar);
//Back bar enabled
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
getSupportActionBar().setDisplayShowHomeEnabled(true);
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case android.R.id.home:
//What happens if you click back
NavUtils.navigateUpFromSameTask(this);
return true;
default:
return super.onOptionsItemSelected(item);
}
}
public void updatePost(){
commentsView.postDelayed(new Runnable() {
#Override
public void run() {
commentsView.smoothScrollToPosition(commentsView.getAdapter().getItemCount());
//getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE);
}
}, 1000);
}
private void checkAdapterIsEmpty () {
if(application.getCommentsRecyclerViewAdapter().getItemCount() == 1){
RelativeLayout.LayoutParams params = (RelativeLayout.LayoutParams) noCommentsView.getLayoutParams();
params.addRule(RelativeLayout.BELOW, R.id.view_post);
noCommentsView.setVisibility(View.VISIBLE);
}
else {
noCommentsView.setVisibility(View.GONE);
}
}
public CommentsHeader getCommentsHeader(String id)
{
System.out.println("Going to inflate header");
CommentsHeader header = new CommentsHeader();
header.setPosterUserId(posterUserId);
header.setPosterName(posterName);
header.setPosterDate(postTimeStamp);
header.setViewStatus(postStatus);
return header;
}
public void populatePost(String id) {
TextView statusMsg = (TextView)findViewById(R.id.view_status);
System.out.println("Post: " + post);
statusMsg.setText(post.getStatus());
//Set profile picture
DraweeController controller = news_feed.getImage(userId);
SimpleDraweeView draweeView = (SimpleDraweeView) findViewById(R.id.poster_picture);
draweeView.setController(controller);
//Set poster's name
TextView posterName = (TextView)findViewById(R.id.poster_name);
posterName.setText(post.getName());
//Set date of when post was created
TextView postDate = (TextView) findViewById(R.id.post_date);
postDate.setText(AndroidUtils.convertDate(post.getTimeStamp()));
}
public String getIntentString(String value){
Bundle extras = getIntent().getExtras();
String result = "";
if (extras != null) {
result = extras.getString(value);
}
return result;
}
#Override
public void onSaveInstanceState(Bundle savedInstanceState) {
// Save the user's current game state
savedInstanceState.putString("postId", postId);
savedInstanceState.putString("tab", tab);
savedInstanceState.putString("userId", userId);
savedInstanceState.putString("name", name);
savedInstanceState.putString("posterUserId", posterUserId);
savedInstanceState.putString("posterName", posterName);
savedInstanceState.putString("postTimeStamp", postTimeStamp);
savedInstanceState.putString("postStatus", postStatus);
// Always call the superclass so it can save the view hierarchy state
super.onSaveInstanceState(savedInstanceState);
}
private void setupActivity(Bundle savedInstanceState) {
if (savedInstanceState != null) {
// Restore value of members from saved state
if(savedInstanceState.containsKey("tab")) {
tab = savedInstanceState.getString("tab");
}
if(savedInstanceState.containsKey("postId")) {
postId = savedInstanceState.getString("postId");
}
if(savedInstanceState.containsKey("userId")) {
userId = savedInstanceState.getString("userId");
}
if(savedInstanceState.containsKey("name")) {
name = savedInstanceState.getString("name");
}
if(savedInstanceState.containsKey("posterUserId")) {
posterUserId = savedInstanceState.getString("posterUserId");
}
if(savedInstanceState.containsKey("posterName")) {
posterName = savedInstanceState.getString("posterName");
}
if(savedInstanceState.containsKey("postTimeStamp")) {
postTimeStamp = savedInstanceState.getString("postTimeStamp");
}
if(savedInstanceState.containsKey("postStatus")) {
postStatus = savedInstanceState.getString("postStatus");
}
} else {
postId = getIntentString("postId");
tab = getIntentString("tab");
userId = getIntentString("userId");
posterUserId = getIntentString("posterUserId");
posterName = getIntentString("posterName");
postTimeStamp = getIntentString("postTimeStamp");
postStatus = getIntentString("postStatus");
// Probably initialize members with default values for a new instance
}
databaseQuery = new DatabaseQuery(this);
application = ((FireBaseApplication) getApplication());
progressOverlay = findViewById(R.id.progress_overlay);
if(application.getName() != null && application.getName() != "") {
name = application.getName();
} else {
if(savedInstanceState != null) {
if(savedInstanceState.containsKey("name")) {
name = savedInstanceState.getString("name");
}
}
}
toolbar = (Toolbar) findViewById(R.id.comments_appbar);
notificationManager = (NotificationManager)
getSystemService(NOTIFICATION_SERVICE);
commentsView = (RecyclerView) findViewById(R.id.view_comments);
noCommentsView = (TextView) findViewById(R.id.no_comments_text);
llm = new LinearLayoutManager(this);
commentsView.setLayoutManager(llm);
}
}
AndroidManifest.xml:
<activity
android:name=".com.tabs.activity.Comments"
android:label="View Post"
android:configChanges="orientation|keyboardHidden"
android:windowSoftInputMode="stateAlwaysHidden|adjustPan"
android:theme="#style/AppTheme.NoActionBar" >
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value=".com.tabs.activity.Comments"
android:configChanges="orientation|keyboardHidden" />
</activity>
I have tried to set my TextView to android:gravity="center_horizontal|center_vertical" or have tried to set android:centerVertical="true" but the former produces the same exact behavior and the latter makes my TextView not even show up. Is there any way I can fix the position of the TextView? Any help would be appreciated, thanks!
Add android:windowSoftInputMode="adjustPan" in activity tag on Manifest.xml
I think configChanges flag shall be added to your manifest file ,to solve this
<activity android:name=".MyActivity"
android:configChanges="orientation|keyboardHidden"
android:label="#string/app_name">
For more details read this post from developer's website
http://developer.android.com/guide/topics/resources/runtime-changes.html
You should read about the android:windowSoftInputMode property that you can add to your Activity in AndroidManifest.xml. You can read about it here: http://developer.android.com/guide/topics/manifest/activity-element.html#wsoft
You have plenty of options there, choose the one that fits your needs.
Have you tried:
android:layout_centerInParent="true" for your TextView, and use android:layout_above="#+id/view_comments"?
Untested, but TextView needs some layout parameters that relates to RelativeLayout.