I am trying to access CallManager class object from com.android.internal.telephony package.
Here is my code:
ClassLoader classLoader = TestActivity.class.getClassLoader();
final ClassLoader classLoader = this.getClass().getClassLoader();
try {
final Class<?> classCallManager =
classLoader.loadClass("com.android.internal.telephony.CallManager");
Log.i("TestActivity", classCallManager);
} catch (final ClassNotFoundException e) {
Log.e("TestActivity", e);
}
Unfortunately, this is throwing a ClassNotFoundException. The same approach allows me to access PhoneFactory, but apparently I'm not allowed to access CallManager.
If I could reach the class, then I'd want to proceed using the class as follows:
Method method_getInstance;
method_getInstance = classCallManager.getDeclaredMethod("getInstance");
method_getInstance.setAccessible(true);
Object callManagerInstance = method_getInstance.invoke(null);
Can anyone help me on this?
Thanks in advance,
Harsha C
I could successfully load CallManager and its methods. However, when I invoke getState(), getActiveFgCallState(), it always return IDLE even when the app receives different call states from TelephonyManager, i.e. TelephonyManager.CALL_STATE_IDLE, TelephonyManager.CALL_STATE_OFFHOOK, TelephonyManager.CALL_STATE_RINGING.
I used the following code to load the class and its methods:
final Class<?> classCallManager = classLoader.loadClass("com.android.internal.telephony.CallManager");
Log.i(TAG, "Class loaded " + classCallManager.toString());
Method methodGetInstance = classCallManager.getDeclaredMethod("getInstance");
Log.i(TAG, "Method loaded " + methodGetInstance.getName());
Object objectCallManager = methodGetInstance.invoke(null);
Log.i(TAG, "Object loaded " + objectCallManager.getClass().getName());
Method methodGetState = classCallManager.getDeclaredMethod("getState");
Log.i(TAG, "Method loaded " + methodGetState.getName());
Log.i(TAG, "Phone state = " + methodGetState.invoke(objectCallManager));
Btw, what I am trying to do is detecting when the phone starts ringing. I saw in the source code that ALERTING is the internal event that I should listen to. Therefore, I tried to use CallManager to get Call.State, rather than Phone.State. I also tried to use registerForPreciseCallStateChanges() of CallManager class but none of approached worked so far.
I had to solve the exact same problem - getting the disconnection cause during call hangup. My solution was to grep the radio logs for the relevant lines. Seems to work - hope it helps.
private void startRadioLogListener() {
new Thread(new Runnable() {
public void run() {
Process process = null;
try {
// Clear the log first
String myCommandClear = "logcat -b radio -c";
Runtime.getRuntime().exec(myCommandClear);
String myCommand = "logcat -b radio";
process = Runtime.getRuntime().exec(myCommand);
Log.e(LogHelper.CAL_MON, "RadioLogProc: " + process);
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(process.getInputStream()));
while (true) {
final String line = bufferedReader.readLine();
if (line != null) {
if (line.contains("disconnectCauseFromCode") || line.contains("LAST_CALL_FAIL_CAUSE")) {
Log.d(LogHelper.CAL_MON, "RadioLog: " + line);
radioLogHandler.post(new Runnable() {
public void run() {
consolePrint("Radio: " + line + "\n");
}
});
}
}
}
} catch (IOException e) {
Log.e(LogHelper.CAL_MON, "Can't get radio log", e);
} finally {
if (process != null) {
process.destroy();
}
}
}
}).start();
}
Have you tried this method found here on this blog?
By loading the Phone.apk might be the clue to getting around the ClassNotFound exception error...
I have written a program that recognize the phone calls and list all recent calls in a list. Maybe you can have a look on this code and it can help I think.
All you need is this:
String state = bundle.getString(TelephonyManager.EXTRA_STATE);
if(state.equalsIgnoreCase(TelephonyManager.EXTRA_STATE_RINGING))
but check this example also:
package org.java.sm222bt;
import org.java.sm222bt.R;
import android.app.ListActivity;
import android.content.Intent;
import android.database.Cursor;
import android.net.Uri;
import android.os.Bundle;
import android.view.ContextMenu;
import android.view.MenuItem;
import android.view.View;
import android.widget.ListAdapter;
import android.widget.SimpleCursorAdapter;
public class MainActivity extends ListActivity {
private CountryDbAdapter db;
private Cursor entrycursor;
private ListAdapter adapter;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//setContentView(R.layout.main);
registerForContextMenu(getListView());
db = new CountryDbAdapter(this);
updateEntry();
}
public void updateEntry(){
db.open();
entrycursor = db.fetchAllEntries();
adapter = new SimpleCursorAdapter(this, R.layout.row, entrycursor, new String[] {"phonenumber"}, new int[] {R.id.number});
setListAdapter(adapter);
db.close();
}
#Override
protected void onResume() {
super.onResume();
updateEntry();
}
public static final int Call = 0;
public static final int SendSMS = 1;
public static final int Share = 2;
public static final int Delete = 3;
public static final int ClearList = 4;
public void onCreateContextMenu(ContextMenu menu, View v,
ContextMenu.ContextMenuInfo menuInfo) {
menu.setHeaderTitle("Select:");
menu.add(0, Call, 0, "Call");
menu.add(0, SendSMS, 0, "Send SMS");
menu.add(0, Share, 0, "Share");
menu.add(0, Delete, 0, "Delete");
menu.add(0, ClearList, 0, "Clear all contacts");
}
#Override
public boolean onContextItemSelected(MenuItem item) {
switch (item.getItemId()) {
case Call:
//System.out.println(entrycursor.getString(1));
//EditText number=(EditText)findViewById(R.id.number);
String toDial="tel:"+entrycursor.getString(1);
//start activity for ACTION_DIAL or ACTION_CALL intent
startActivity(new Intent(Intent.ACTION_DIAL, Uri.parse(toDial)));
//update(entryCursor.getLong(0));
return true;
case SendSMS:
//EditText number=(EditText)findViewById(R.id.number);
//EditText msg=(EditText)findViewById(R.id.msg);
String sendUri="smsto:"+entrycursor.getString(1);
Intent sms=new Intent(Intent.ACTION_SENDTO,
Uri.parse(sendUri));
//sms.putExtra("sms_body", msg.getText().toString());
startActivity(sms);
return true;
case Share:
Intent i=new Intent(Intent.ACTION_SEND);
i.setType("text/plain");
i.putExtra(Intent.EXTRA_SUBJECT, "Hello");
i.putExtra(Intent.EXTRA_TEXT, "Sharing this number"+entrycursor.getString(1));
startActivity(Intent.createChooser(i,
entrycursor.getString(1)));
return true;
case Delete:
db.open();
db.deleteEntry(entrycursor.getLong(0));
db.close();
updateEntry();
return true;
case ClearList:
db.open();
db.deleteEntry();
db.close();
updateEntry();
return true;
default:
return super.onContextItemSelected(item);
}
}
}
and here is the incomming call receiver:
package org.java.sm222bt;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.database.Cursor;
import android.os.Bundle;
import android.telephony.TelephonyManager;
import android.widget.ListAdapter;
import android.widget.SimpleCursorAdapter;
public class IncomingCallReceiver extends BroadcastReceiver {
CountryDbAdapter db;
#Override
public void onReceive(Context context, Intent intent) {
// TODO Auto-generated method stub
Bundle bundle = intent.getExtras();
if(null == bundle)
return;
String state = bundle.getString(TelephonyManager.EXTRA_STATE);
if(state.equalsIgnoreCase(TelephonyManager.EXTRA_STATE_RINGING))
{
String phonenumber = bundle.getString(TelephonyManager.EXTRA_INCOMING_NUMBER);
System.out.println(phonenumber);
db = new CountryDbAdapter(context);
db.open();
db.insertEntry(phonenumber);
db.fetchAllEntries();
db.close();
}
}}
I understand that you want to detect when the call is disconnected. You can instead use the PhoneStateListener.LISTEN_CALL_STATE. For example:
final TelephonyManager telephony = (TelephonyManager)
getSystemService(Context.TELEPHONY_SERVICE);
telephony.listen(new PhoneStateListener() {
public void onCallStateChanged(final int state,
final String incomingNumber) {
switch (state) {
case TelephonyManager.CALL_STATE_IDLE:
break;
case TelephonyManager.CALL_STATE_OFFHOOK:
Log.d("TestActivity", "Call disconnected");
break;
case TelephonyManager.CALL_STATE_RINGING:
break;
default:
break;
}
}
}, PhoneStateListener.LISTEN_CALL_STATE);
Use this :
telephone = (TelephonyManager)getSystemService(Context.TELEPHONY_SERVICE);
private PhoneStateListener psl = new PhoneStateListener() {
#Override
public void onCallStateChanged (int state, String incomingNumber)
{
state = telephone.getCallState();
switch(state) {
case android.telephony.TelephonyManager.CALL_STATE_IDLE:
if (callsucces ) act();
break;
case android.telephony.TelephonyManager.CALL_STATE_RINGING:
callsucces = true;
break;
case android.telephony.TelephonyManager.CALL_STATE_OFFHOOK:
callsucces = true;
break;
}
}
};
private void call(String pnum) {
try {
callIntent = new Intent(Intent.ACTION_CALL);
callsucces = false;
if (telephone.getNetworkType() != 0) {
if (telephone.getCallState() == TelephonyManager.CALL_STATE_IDLE) {
callIntent.setData(Uri.parse("tel:"+pnum));
startActivity(callIntent);
telephone.listen(psl,PhoneStateListener.LISTEN_CALL_STATE);
}
} else act();
//callIntent.ACTION_NEW_OUTGOING_CALL
} catch (ActivityNotFoundException activityException) {
Toast.makeText(getBaseContext(), "Call failed",Toast.LENGTH_SHORT).show();
act();
}
}
Did you add READ_PHONE_STATE in AndroidManifest.xml ?
I think you miss that one.
Related
I am completely new to Android Studio and just learned Object-oriented programming. My project requires me to build something on open-source code. I added a new menu item to a menu and want to start another activity once the user clicks the menu item with id: plot. I followed a recipe on the internet but got an error with it. It said 'method call expected' which means Terminal Fragment may be a method. I got confused, as I thought it is a class(an activity). Could anyone give me instructions to start an activity (turn to the next page with a different activity) in this case? What will be the simplest way to do this? Much Appreciated.
I added this in onOptionsItemSelected(MenuItem item).
if (id == R.id.plot){
Intent intent = new Intent(TerminalFragment.this, MainActivity2.class);
startActivity(intent);
}
TerminalFragment.java (entire code)
package de.kai_morich.simple_bluetooth_le_terminal;
import android.app.Activity;
import android.app.AlertDialog;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Bundle;
import android.os.IBinder;
import android.text.Editable;
import android.text.Spannable;
import android.text.SpannableStringBuilder;
import android.text.method.ScrollingMovementMethod;
import android.text.style.ForegroundColorSpan;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;
import android.widget.Toast;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
public class TerminalFragment extends Fragment implements ServiceConnection, SerialListener {
private MenuItem menuItem;
private enum Connected { False, Pending, True }
private String deviceAddress;
private SerialService service;
private TextView receiveText;
private TextView sendText;
private TextUtil.HexWatcher hexWatcher;
private Connected connected = Connected.False;
private boolean initialStart = true;
private boolean hexEnabled = false;
private boolean pendingNewline = false;
private String newline = TextUtil.newline_crlf;
/*
* Lifecycle
*/
#Override
public void onCreate(#Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setHasOptionsMenu(true);
//Register with activity
// You must inform the system that your app bar fragment is participating in the population of the options menu.
// tells the system that your fragment would like to receive menu-related callbacks.
setRetainInstance(true);
deviceAddress = getArguments().getString("device");
}
#Override
public void onDestroy() {
if (connected != Connected.False)
disconnect();
getActivity().stopService(new Intent(getActivity(), SerialService.class));
super.onDestroy();
}
#Override
public void onStart() {
super.onStart();
if(service != null)
service.attach(this);
else
getActivity().startService(new Intent(getActivity(), SerialService.class)); // prevents service destroy on unbind from recreated activity caused by orientation change
}
#Override
public void onStop() {
if(service != null && !getActivity().isChangingConfigurations())
service.detach();
super.onStop();
}
#SuppressWarnings("deprecation") // onAttach(context) was added with API 23. onAttach(activity) works for all API versions
#Override
public void onAttach(#NonNull Activity activity) {
super.onAttach(activity);
getActivity().bindService(new Intent(getActivity(), SerialService.class), this, Context.BIND_AUTO_CREATE);
}
#Override
public void onDetach() {
try { getActivity().unbindService(this); } catch(Exception ignored) {}
super.onDetach();
}
#Override
public void onResume() {
super.onResume();
if(initialStart && service != null) {
initialStart = false;
getActivity().runOnUiThread(this::connect);
}
}
#Override
public void onServiceConnected(ComponentName name, IBinder binder) {
service = ((SerialService.SerialBinder) binder).getService();
service.attach(this);
if(initialStart && isResumed()) {
initialStart = false;
getActivity().runOnUiThread(this::connect);
}
}
#Override
public void onServiceDisconnected(ComponentName name) {
service = null;
}
/*
* UI
*/
#Override
public View onCreateView(#NonNull LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_terminal, container, false);
receiveText = view.findViewById(R.id.receive_text); // TextView performance decreases with number of spans
receiveText.setTextColor(getResources().getColor(R.color.colorRecieveText)); // set as default color to reduce number of spans
receiveText.setMovementMethod(ScrollingMovementMethod.getInstance());
sendText = view.findViewById(R.id.send_text);
hexWatcher = new TextUtil.HexWatcher(sendText);
hexWatcher.enable(hexEnabled);
sendText.addTextChangedListener(hexWatcher);
sendText.setHint(hexEnabled ? "HEX mode" : "");
View sendBtn = view.findViewById(R.id.send_btn);
sendBtn.setOnClickListener(v -> send(sendText.getText().toString()));
return view;
}
#Override
public void onCreateOptionsMenu(#NonNull Menu menu, MenuInflater inflater) {
inflater.inflate(R.menu.menu_terminal, menu);
menu.findItem(R.id.hex).setChecked(hexEnabled);
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = item.getItemId();
if (id == R.id.clear) {
receiveText.setText("");
return true;
} if (id == R.id.plot){
Intent intent = new Intent(TerminalFragment.this, MainActivity2.class);
startActivity(intent);
}else if (id == R.id.newline) {
String[] newlineNames = getResources().getStringArray(R.array.newline_names);
String[] newlineValues = getResources().getStringArray(R.array.newline_values);
int pos = java.util.Arrays.asList(newlineValues).indexOf(newline);
AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
builder.setTitle("Newline");
builder.setSingleChoiceItems(newlineNames, pos, (dialog, item1) -> {
newline = newlineValues[item1];
dialog.dismiss();
});
builder.create().show();
return true;
} else if (id == R.id.hex) {
hexEnabled = !hexEnabled;
sendText.setText("");
hexWatcher.enable(hexEnabled);
sendText.setHint(hexEnabled ? "HEX mode" : "");
item.setChecked(hexEnabled);
return true;
} else {
return super.onOptionsItemSelected(item);
}
}
/*
* Serial + UI
*/
private void connect() {
try {
BluetoothAdapter bluetoothAdapter = BluetoothAdapter.getDefaultAdapter();
BluetoothDevice device = bluetoothAdapter.getRemoteDevice(deviceAddress);
status("connecting...");
connected = Connected.Pending;
SerialSocket socket = new SerialSocket(getActivity().getApplicationContext(), device);
service.connect(socket);
} catch (Exception e) {
onSerialConnectError(e);
}
}
private void disconnect() {
connected = Connected.False;
service.disconnect();
}
private void send(String str) {
if(connected != Connected.True) {
Toast.makeText(getActivity(), "not connected", Toast.LENGTH_SHORT).show();
return;
}
try {
String msg;
byte[] data;
if(hexEnabled) {
StringBuilder sb = new StringBuilder();
TextUtil.toHexString(sb, TextUtil.fromHexString(str));
TextUtil.toHexString(sb, newline.getBytes());
msg = sb.toString();
data = TextUtil.fromHexString(msg);
} else {
msg = str;
data = (str + newline).getBytes();
}
SpannableStringBuilder spn = new SpannableStringBuilder(msg + '\n');
spn.setSpan(new ForegroundColorSpan(getResources().getColor(R.color.colorSendText)), 0, spn.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
receiveText.append(spn);
service.write(data);
} catch (Exception e) {
onSerialIoError(e);
}
}
private void receive(byte[] data) {
if(hexEnabled) {
receiveText.append("Hello" + TextUtil.toHexString(data) + '\n');
} else {
String msg = new String(data);
if(newline.equals(TextUtil.newline_crlf) && msg.length() > 0) {
// don't show CR as ^M if directly before LF
msg = msg.replace(TextUtil.newline_crlf, TextUtil.newline_lf);
// special handling if CR and LF come in separate fragments
if (pendingNewline && msg.charAt(0) == '\n') {
Editable edt = receiveText.getEditableText();
if (edt != null && edt.length() > 1)
edt.replace(edt.length() - 2, edt.length(), "");
}
pendingNewline = msg.charAt(msg.length() - 1) == '\r';
}
receiveText.append(TextUtil.toCaretString(msg, newline.length() != 0)); //print out data
}
}
private void status(String str) {
SpannableStringBuilder spn = new SpannableStringBuilder(str + '\n');
spn.setSpan(new ForegroundColorSpan(getResources().getColor(R.color.colorStatusText)), 0, spn.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
receiveText.append(spn);
}
/*
* SerialListener
*/
#Override
public void onSerialConnect() {
status("connected");
connected = Connected.True;
}
#Override
public void onSerialConnectError(Exception e) {
status("connection failed: " + e.getMessage());
disconnect();
}
#Override
public void onSerialRead(byte[] data) {
receive(data);
}
#Override
public void onSerialIoError(Exception e) {
status("connection lost: " + e.getMessage());
disconnect();
}
}
menu_terminal.xml
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:android="http://schemas.android.com/apk/res/android">
<item
android:id="#+id/plot"
android:title="PLOTDATA"
app:showAsAction="always" />
<item
android:id="#+id/clear"
android:icon="#drawable/ic_delete_white_24dp"
android:title="Clear"
app:showAsAction="always" />
<item
android:id="#+id/newline"
android:title="Newline"
app:showAsAction="never" />
<item
android:id="#+id/hex"
android:title="HEX Mode"
android:checkable="true"
app:showAsAction="never" />
</menu>
Here, TerminalFragment is a fragment, not an activity. And so, instead of using TerminalFragment.this in new Intent(), you should use getActivity().
So, the final code would look something like this:
Intent intent = new Intent(getActivity(), MainActivity2.class);
startActivity(intent);
You can also check this: Intent from Fragment to Activity
I have a custom ListView with BaseAdapter. In this custom ListView when a user clicks on any particular text, it speaks the text but the problem is that when any user clicks on the back button how to stop this text from the BaseAdapter. I know how to stop from an Activity but don't know how to stop from BaseAdapter when the user presses back button. Here is my code:
package bible.swordof.God;
import android.app.Activity;
import android.content.ContentValues;
import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.graphics.Color;
import android.os.Vibrator;
import android.speech.tts.TextToSpeech;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.CompoundButton;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import android.widget.Toast;
import android.widget.ToggleButton;
import java.util.ArrayList;
import java.util.List;
import java.util.Locale;
import java.util.zip.Inflater;
import es.dmoral.toasty.Toasty;
import petrov.kristiyan.colorpicker.ColorPicker;
import static android.content.Context.MODE_PRIVATE;
public class BaseAdopter extends BaseAdapter implements TextToSpeech.OnInitListener{
public BaseAdopter(Context context, List<String> versenumber, List<String> verseid, List<String> verselist, List<String> refernce) {
this.context = context;
this.versenumber = versenumber;
this.verseid = verseid;
this.verselist = verselist;
this.refernce = refernce;
}
ALLVERSE allverse;
ArrayList<String> colors;
private Context context;
private List<String> versenumber;
private List<String>verseid;
private List<String> verselist;
private List<String> refernce;
TextToSpeech textToSpeech;
private DatabaseHelper mDBHelper;
private SQLiteDatabase mDb;
#Override
public int getCount() {
return versenumber.size();
}
#Override
public Object getItem(int position) {
return null;
}
#Override
public long getItemId(int position) {
return 0;
}
#Override
public View getView(final int position, View convertView, ViewGroup parent) {
LayoutInflater inflater = (LayoutInflater)context.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
View view=inflater.inflate(R.layout.versedisplayrow,parent,false);
textToSpeech = new TextToSpeech(context, this);
final TextView verseno;
final TextView verselistview;
ImageView share;
ToggleButton addfavoruite;
ImageView speakverse;
final LinearLayout linearLayout;
verseno=(TextView)view.findViewById(R.id.versenumber);
verseno.setText(versenumber.get(position));
verselistview=(TextView)view.findViewById(R.id.verse);
verselistview.setText(verselist.get(position));
addfavoruite=(ToggleButton)view.findViewById(R.id.adbookmark);
linearLayout=(LinearLayout)view.findViewById(R.id.layout);
share=(ImageView)view.findViewById(R.id.share);
speakverse=(ImageView)view.findViewById(R.id.speak);
if(DefaultSettings.nightmode(context)){
linearLayout.setBackgroundColor(Color.parseColor("#363437"));
verselistview.setTextColor(Color.parseColor("#ffffff"));
verseno.setTextColor(Color.parseColor("#ffffff"));
}
speakverse.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
singleverse(verselist.get(position).toString());
}
});
int a=position+1;
colors=new ArrayList<>();
colors.add("#e0e0eb");
colors.add("#ccffff");
colors.add("#ffe6ff");
colors.add("#ffffcc");
colors.add("#ccffcc");
colors.add("#e6f2ff");
SharedPreferences sharedPreferences=context.getSharedPreferences("DATA",MODE_PRIVATE);
int getverse=sharedPreferences.getInt("versenumber",1);
if(a==getverse){
if(DefaultSettings.highlight(context)){
DefaultSettings.color(context);
linearLayout.setBackgroundColor(DefaultSettings.colorpicked);
}
}
if(Checkisfavourite("favourite","id",verseid.get(position)))
{
if(verseid.get(position).equals(verseid.get(position))){
addfavoruite.setChecked(true);
}else {
addfavoruite.setChecked(false);
}
}
addfavoruite.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
#Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
if(isChecked){
mDBHelper = new DatabaseHelper(context);
mDb = mDBHelper.getWritableDatabase();
ContentValues contentValues=new ContentValues();
contentValues.put("id",verseid.get(position));
contentValues.put("bookname",refernce.get(position));
contentValues.put("versenumber",versenumber.get(position));
contentValues.put("verse",verselist.get(position));
long check=mDb.insert("favourite",null,contentValues);
Toasty.success(context, "Added in favouite", Toast.LENGTH_SHORT, true).show();
}
else {
mDBHelper = new DatabaseHelper(context);
mDb = mDBHelper.getWritableDatabase();
long delete= mDb.delete("favourite","id=?",new String[]{verseid.get(position)});
Toasty.error(context, "Remove in favouite", Toast.LENGTH_SHORT, true).show();
}
}
});
share.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Toasty.info(context, "Sharing a verse.", Toast.LENGTH_SHORT, true).show();
Intent sendIntent = new Intent();
sendIntent.setAction(Intent.ACTION_SEND);
sendIntent.putExtra(Intent.EXTRA_TEXT, refernce.get(position) + ":" + versenumber.get(position) + '\n' + verselist.get(position) +
+'\n' +'\n' +'\n' +"https://play.google.com/store/apps/details?id=bible.swordof.God");
sendIntent.setType("text/plain");
context.startActivity(sendIntent);
}
});
/* linearLayout.setOnLongClickListener(new View.OnLongClickListener() {
#Override
public boolean onLongClick(View v) {
//Toasty.success(activity, "PICK COLOR", Toast.LENGTH_SHORT, true).show();
Vibrator vibe = (Vibrator)context.getSystemService(Context.VIBRATOR_SERVICE);
vibe.vibrate(100);
mDBHelper = new DatabaseHelper(context);
mDb = mDBHelper.getWritableDatabase();
ContentValues contentValues=new ContentValues();
contentValues.put("verseid",colors.get(position));
final long check=mDb.insert("highlight",null,contentValues);
//id get
//postion
//Toast.makeText(activity, ""+getItemId(position), Toast.LENGTH_SHORT).show();
ColorPicker colorPicker = new ColorPicker(context);
colorPicker.setColors(colors).setColumns(4).setTitle("HIGHLIGHT VERSE").setRoundColorButton(true).setOnChooseColorListener(new ColorPicker.OnChooseColorListener() {
#Override
public void onChooseColor(int position, int color) {
linearLayout.setBackgroundColor(Color.parseColor(colors.get(position)));
}
#Override
public void onCancel() {
}
}).show();
return false;
}
});
*/
return view;
}
public boolean Checkisfavourite(String TableName, String dbfield, String fieldValue) {
mDBHelper = new DatabaseHelper(context);
mDb = mDBHelper.getReadableDatabase();
String Query = "Select * from " + TableName + " where " + dbfield + " = " + fieldValue;
Cursor cursor = mDb.rawQuery(Query, null);
if(cursor.getCount() <= 0){
cursor.close();
// Toast.makeText(activity, "false", Toast.LENGTH_SHORT).show();
return false;
}else {
// Toast.makeText(activity, "TRUE", Toast.LENGTH_SHORT).show();
}
cursor.close();
return true;
}
public boolean colorcheck(String TableName, String dbfield, String fieldValue) {
mDBHelper = new DatabaseHelper(context);
mDb = mDBHelper.getReadableDatabase();
String Query = "Select * from " + TableName + " where " + dbfield + " = " + fieldValue;
Cursor cursor = mDb.rawQuery(Query, null);
if(cursor.getCount() <= 0){
cursor.close();
// Toast.makeText(activity, "false", Toast.LENGTH_SHORT).show();
return false;
}else {
// Toast.makeText(activity, "TRUE", Toast.LENGTH_SHORT).show();
}
cursor.close();
return true;
}
#Override
public void onInit(int status) {
if (status == TextToSpeech.SUCCESS) {
int result = textToSpeech.setLanguage(Locale.US);
// tts.setPitch(5); // set pitch level
// tts.setSpeechRate(2); // set speech speed rate
if (result == TextToSpeech.LANG_MISSING_DATA
|| result == TextToSpeech.LANG_NOT_SUPPORTED) {
Log.e("TTS", "Language is not supported");
} else {
}
} else {
Log.e("TTS", "Initilization Failed");
}
}
private void singleverse(String text) {
DefaultSettings.speed(context);
textToSpeech.setPitch(DefaultSettings.pitchvalue);
textToSpeech.setSpeechRate(DefaultSettings.speedvalue);
textToSpeech.speak(text, TextToSpeech.QUEUE_FLUSH, null);
}
public void stop(){
if (textToSpeech != null) {
textToSpeech.stop();
textToSpeech.shutdown();
}
}
}
The main problem is that your TextToSpeech object belongs to your BaseAdapter when it should belong to the parent activity.
Instead of housing it in the adapter and calling speak on it every time the user clicks an item, I would instead house it in the parent activity and use an "interface callback" that sends a message to the parent when the user clicks an item, sending back the string to speak. This callback relationship works the exact same way as the TextToSpeech.OnInitListener callback that you're already using.
Once the TTS belongs to the parent activity, you can use the activity lifecycle functions to control the shutdown of the TTS like normal.
If you study and understand the following, you should be able to merge it into your code and get a working solution:
Make these changes to your custom BaseAdapter:
// Remove the TextToSpeech object from this class.
public class MyBaseAdapter {
// add this interface definition to your adapter
public interface SpeechClickSubscriber {
void stringNeedsToBeSpoken(String verse);
}
// add this property (the subscriber)
private SpeechClickSubscriber speechClickSubscriber;
// *add* this functionality to your adapter's existing constructor
MyBaseAdapter(SpeechClickSubscriber parent) {
speechClickSubscriber = parent;
}
//...
// change this section of code in your getView() method
speakverse.setOnClickListener(new View.OnClickListener()
{
#Override
public void onClick (View v){
// change this...
// singleverse(verselist.get(position).toString());
// to this:
speechClickSubscriber.stringNeedsToBeSpoken(verselist.get(position).toString());
}
});
// ...
}
Make these changes to your MainActivity (or whatever your parent activity is):
// add the SpeechClickSubscriber implementation
public class MainActivity extends AppCompatActivity implements MyBaseAdapter.SpeechClickSubscriber, TextToSpeech.OnInitListener {
MyBaseAdapter adapter;
TextToSpeech textToSpeech;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// using app context is better and less error prone.
textToSpeech = new TextToSpeech(getApplicationContext(), this);
}
// *add* this method to this activity (this is the answer to your question)
#Override
protected void onStop() {
super.onStop();
stopTTS();
}
// use this method as your "onStart()" method...
// this will help prevent any user input processing until the tts is initialized.
private void start_Activity_Because_TTS_Has_Initialized() {
adapter = new MyBaseAdapter(this);
}
// *MOVE* this method from your base adapter to this (parent) activity:
#Override
public void onInit(int status) {
if (status == TextToSpeech.SUCCESS) {
int result = textToSpeech.setLanguage(Locale.US);
// tts.setPitch(5); // set pitch level
// tts.setSpeechRate(2); // set speech speed rate
if (result == TextToSpeech.LANG_MISSING_DATA
|| result == TextToSpeech.LANG_NOT_SUPPORTED) {
Log.e("TTS", "Language is not supported");
} else {
}
} else {
Log.e("TTS", "Initilization Failed");
}
}
// *move* and *rename* this method from your adapter to the parent activity:
// from:
/*
private void singleverse(String text) {
DefaultSettings.speed(context);
textToSpeech.setPitch(DefaultSettings.pitchvalue);
textToSpeech.setSpeechRate(DefaultSettings.speedvalue);
textToSpeech.speak(text, TextToSpeech.QUEUE_FLUSH, null);
} */
// to:
#Override
public void stringNeedsToBeSpoken(String verse) {
Log.i("XXX","stringNeedsToBeSpoken() was called because the user clicked an item.");
Log.i("XXX","This method is being called because this activity subscribes to the callback we created and added to our base adapter.");
//DefaultSettings.speed(context); // <----------------- I don't know what this does.
// I'm assuming that DefaultSettings is a static class you have made.
textToSpeech.setPitch(DefaultSettings.pitchvalue);
textToSpeech.setSpeechRate(DefaultSettings.speedvalue);
textToSpeech.speak(verse, TextToSpeech.QUEUE_FLUSH, null);
}
public void stopTTS(){
if (textToSpeech != null) {
textToSpeech.stop();
textToSpeech.shutdown();
}
}
}
Why is my activity unable to upload pictures taken by camera while it easily uploads the picture picked from the gallery?
The picture uploaded through the gallery is available on the server but the file(picture) taken through the camera is not found on the server after the API hit.
Opening the directory on the server gives 'File not found' error for the file uploaded via camera.
Here is my code:
import android.content.DialogInterface;
import android.content.Intent;
import android.content.IntentFilter;
import android.content.pm.PackageManager;
import android.database.Cursor;
import android.graphics.Matrix;
import android.media.ExifInterface;
import android.net.ConnectivityManager;
import android.net.Uri;
import android.os.Build;
import android.os.Environment;
import android.provider.MediaStore;
import android.support.v4.content.FileProvider;
import android.support.v7.app.ActionBar;
import android.support.v7.app.AlertDialog;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.support.v7.widget.AppCompatCheckBox;
import android.view.MenuItem;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.Spinner;
import android.widget.TextView;
import android.widget.Toast;
import static com.app.engage.Interfaces.Keys.userDetails.*;
import com.app.engage.Interfaces.ApiResponse;
import com.app.engage.Interfaces.NetworkConnectivityListener;
import com.app.engage.R;
import com.app.engage.Utilities.ConnectionDetector;
import com.app.engage.Utilities.GetServerData;
import com.app.engage.Utilities.ImageOnlyOptionsDialog;
import com.app.engage.Utilities.ProgressDialog;
import com.app.engage.Utilities.RoleSectDialog;
import com.app.engage.Utilities.RoundCorner;
import com.app.engage.Utilities.SharedPreference_Main;
import com.app.engage.Utilities.Utilities;
import com.bumptech.glide.Glide;
import java.io.File;
import java.io.IOException;
import java.net.URI;
import java.net.URISyntaxException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import com.app.engage.Interfaces.OnButtonClicked;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
public class SignupActivity extends AppCompatActivity implements AdapterView.OnItemSelectedListener, ApiResponse.Api_hit, View.OnClickListener {
private TextView toolbarText;
public static TextView selections;
private ProgressDialog progressDialog;
private String selected_role = null;
private String selectedRole = "", selectedOrgType = "";
public static String selectedNatPriArea = "";
private ArrayList<String> role_list, org_type, nat_pri_area;
private ApiResponse apiResponse;
private ImageView dp;
private Uri uriFilePath;
private int REQUEST_CODE_CAMERA = 1002;
private int REQUEST_PICK_IMAGE = 1003;
private AlertDialog.Builder builder;
private TextView upload_dp;
private AppCompatCheckBox stayLoggedIn;
private Spinner roleSpinner, organisationTypeSpinner;
private Button signUp;
private SharedPreference_Main sharedPreference_main;
private String mCurrentPhotoPath;
// private Utilities utilities;
private TextView select_nat_pri_area;
private ConnectionDetector receiver;
private EditText fullName, email, orgName, password, reEnterPassword;
private File file = null;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_signup);
getWindow().setBackgroundDrawableResource(R.drawable.blurred_background); //setting background here
android.support.v7.widget.Toolbar toolbar = findViewById(R.id.app_bar);
setSupportActionBar(toolbar);
ActionBar ab = getSupportActionBar();
role_list = new ArrayList<>(); //arraylist that will hold the roles coming from the server
org_type = new ArrayList<>();//arraylist that will hold the roles coming from the server
nat_pri_area = new ArrayList<>();
sharedPreference_main = new SharedPreference_Main(this);
ab.setDisplayHomeAsUpEnabled(true);
ab.setHomeAsUpIndicator(R.drawable.white_back_icon_for_toolbar);
toolbarText = findViewById(R.id.toolbarText);
select_nat_pri_area = findViewById(R.id.nat_pri_areaaa);
toolbarText.setText("Sign Up");
apiResponse = new ApiResponse(this);
roleSpinner = findViewById(R.id.select_role_spinner);
organisationTypeSpinner = findViewById(R.id.organisation_type_spinner);
fullName = findViewById(R.id.full_name_editText);
email = findViewById(R.id.email_editText_signUp);
password = findViewById(R.id.pass_edit_text);
reEnterPassword = findViewById(R.id.reEnterPword);
orgName = findViewById(R.id.org_edit_text);
selections = findViewById(R.id.selectionss);
signUp = findViewById(R.id.signUp_Button);
dp = findViewById(R.id.dp);
progressDialog = new ProgressDialog(this);
select_nat_pri_area.setOnClickListener(this);
upload_dp = findViewById(R.id.upload_dp);
dp.setOnClickListener(this);
selections.setOnClickListener(this);
upload_dp.setOnClickListener(this);
// utilities = new Utilities(this);
receiver = new ConnectionDetector(new NetworkConnectivityListener() {
#Override
public void onNetworkConnected() //if network connection is available
{
if (role_list.size() <= 0 || org_type.size() <= 0 || nat_pri_area.size() <= 0) {
getData();
}
}
#Override
public void onNetworkDisconnected() {
displayAlert();
}
}, this);
// sharedPreference_main = SharedPreference_Main.getInstance(this);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) //initialising the AlertDialogue builder
{
builder = new AlertDialog.Builder(this, android.R.style.Theme_Material_Dialog_Alert);
} else {
builder = new AlertDialog.Builder(this);
}
roleSpinner.setOnItemSelectedListener(this);
organisationTypeSpinner.setOnItemSelectedListener(org_type_selection);
dp.setOnClickListener(this);
upload_dp.setOnClickListener(this);
// natPriorityAreaSpinner.setAdapter(adapterSetter(priorityArea));
signUp.setOnClickListener(this);
}
private ArrayAdapter<String> adapterSetter(ArrayList<String> data) //to temporarily populate the spinners
{
ArrayAdapter<String> adapter = new ArrayAdapter<String>(
this, R.layout.custom_spinner, data);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
return adapter;
}
#Override
protected void onPause() {
super.onPause();
unregisterReceiver(receiver);
}
#Override
protected void onResume() {
super.onResume();
IntentFilter filter = new IntentFilter(ConnectivityManager.CONNECTIVITY_ACTION);
registerReceiver(receiver, filter);
receiver.isNetworkAvailable();
//checkConnection();
}
public void signup() {
if (!validate()) { //if the conditions in the validate function are not met return
onSignupFailed();
Toast.makeText(this, "Something went wrong sign-up failed", Toast.LENGTH_SHORT).show();
return;
} else {
Toast.makeText(this, "signing up", Toast.LENGTH_SHORT).show();
// signUp.setEnabled(false);
progressDialog.progressDialogStart("Please Wait...");
try {
apiResponse.hitVolleyMultipartApi(this, "signup", getparams(), prof_pic, file);
} catch (Exception e) {
Toast.makeText(this, e.getMessage(), Toast.LENGTH_SHORT).show();
e.printStackTrace();
}
}
// TODO: Implement your own signup logic here.'
// save();
}
public void onSignupSuccess() //if signup is successful
{
signUp.setEnabled(true);
setResult(RESULT_OK, null);
//Toast.makeText(this, "snkflsndkfl", Toast.LENGTH_SHORT).show();
Intent i = new Intent(this, HomeActivity.class);
//i.putExtra("Back Functionality", true);
startActivity(i);
finish();
}
public void onSignupFailed() {
Toast.makeText(getBaseContext(), "Signup failed", Toast.LENGTH_LONG).show();
signUp.setEnabled(true);
}
public boolean validate() //to check the entered information
{
boolean valid = true;
String name = fullName.getText().toString();
String mail = email.getText().toString();
String pword = password.getText().toString();
String org_Name = orgName.getText().toString();
String reEnterPword = reEnterPassword.getText().toString();
if (name.isEmpty() || name.length() < 3) {
fullName.setError("at least 3 characters", null);
valid = false;
} else {
fullName.setError(null);
}
if (mail.isEmpty() || !android.util.Patterns.EMAIL_ADDRESS.matcher(mail).matches()) {
email.setError("enter a valid email address", null);
valid = false;
} else {
email.setError(null);
}
if (org_Name.isEmpty()) {
orgName.setError("Please enter the organisation's name", null);
valid = false;
} else {
orgName.setError(null);
}
if (pword.isEmpty() || password.length() < 4 || password.length() > 10) {
password.setError("between 4 and 10 alphanumeric characters", null);
valid = false;
} else {
password.setError(null);
}
if (reEnterPword.isEmpty() || reEnterPassword.length() < 4 || reEnterPassword.length() > 10 || !(reEnterPword.equals(pword))) {
reEnterPassword.setError("Password Do not match", null);
valid = false;
} else {
reEnterPassword.setError(null);
}
return valid;
}
#Override
public void onItemSelected(AdapterView<?> adapterView, View view, int i, long l) {
switch (i) {
case 0:
selectedRole = "Facilitator";
break;
case 1:
selectedRole = "Provider Administrator";
break;
case 2:
selectedRole = "Provider Executive";
break;
case 3:
selectedRole = "School PLD Administrator";
break;
case 4:
selectedRole = "MOE National Priority";
break;
case 5:
selectedRole = "Senior Leadership";
break;
case 6:
selectedRole = "Teacher";
break;
}
}
#Override
public void onNothingSelected(AdapterView<?> adapterView) {
}
AdapterView.OnItemSelectedListener org_type_selection = new AdapterView.OnItemSelectedListener() //for organisation type selection
{
#Override
public void onItemSelected(AdapterView<?> adapterView, View view, int i, long l) {
switch (i) {
case 0:
selectedOrgType = "Education";
break;
case 1:
selectedOrgType = "IT";
break;
case 2:
selectedOrgType = "Medical";
break;
case 3:
selectedOrgType = "";
break;
case 4:
selectedOrgType = "";
break;
case 5:
selectedOrgType = "";
break;
case 6:
selectedOrgType = "";
break;
}
}
#Override
public void onNothingSelected(AdapterView<?> adapterView) {
}
};
#Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case android.R.id.home:
finish();
}
return super.onOptionsItemSelected(item);
}
#Override
public void onClick(View view) {
switch (view.getId()) {
case R.id.dp:
case R.id.upload_dp:
ImageOnlyOptionsDialog imageOnlyOptionsDialog = new ImageOnlyOptionsDialog();
imageOnlyOptionsDialog.setonButtonClickListener(new OnButtonClicked() {
#Override
public void onButtonCLick(int buttonId) {
switch (buttonId) {
case R.id.btnCamera:
startCamera();
break;
case R.id.btnGallery:
pickFromGallery();
break;
default:
break;
}
}
});
imageOnlyOptionsDialog.show(getSupportFragmentManager(), ImageOnlyOptionsDialog.class.getSimpleName());
break;
case R.id.signUp_Button:
signup();
break;
case R.id.nat_pri_areaaa:
case R.id.selectionss:
Bundle data = new Bundle();
data.putStringArrayList("pri_areas", nat_pri_area);
RoleSectDialog roleSectDialog = new RoleSectDialog();
roleSectDialog.setArguments(data);
roleSectDialog.show(getSupportFragmentManager(), RoleSectDialog.class.getSimpleName());
roleSectDialog.setonButtonClickListener(new OnButtonClicked() {
#Override
public void onButtonCLick(int buttonId) {
switch (buttonId) {
case R.id.k:
break;
default:
break;
}
}
});
break;
default:
break;
}
}
public void startCamera() {
PackageManager packageManager = this.getPackageManager();
if (packageManager.hasSystemFeature(PackageManager.FEATURE_CAMERA)) {
File mainDirectory = new File(Environment.getExternalStorageDirectory(), "MyFolder/tmp");
if (!mainDirectory.exists())
mainDirectory.mkdirs();
Calendar calendar = Calendar.getInstance();
uriFilePath = Uri.fromFile(new File(mainDirectory, "IMG_" + calendar.getTimeInMillis() + ".jpeg"));
Intent intent1 = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
intent1.putExtra(MediaStore.EXTRA_OUTPUT, uriFilePath);
startActivityForResult(intent1, REQUEST_CODE_CAMERA);
}
}
public void pickFromGallery() //this is the intent creation for picking image from gallery
{
Intent intent = new Intent(Intent.ACTION_PICK);
intent.setType("image/*");
startActivityForResult(Intent.createChooser(intent, "Complete action using"), REQUEST_PICK_IMAGE);
}
public void onActivityResult(int requestCode, int resultCode, Intent data) //this receives the intent's result
{
if (requestCode == REQUEST_CODE_CAMERA) {
if (resultCode == RESULT_OK) {
try {
ExifInterface exif = new ExifInterface(uriFilePath.getPath());
int orientation = exif.getAttributeInt(
ExifInterface.TAG_ORIENTATION,
ExifInterface.ORIENTATION_NORMAL);
Matrix matrix = new Matrix();
switch (orientation) {
case ExifInterface.ORIENTATION_ROTATE_90:
matrix.postRotate(90);
break;
case ExifInterface.ORIENTATION_ROTATE_180:
matrix.postRotate(180);
break;
case ExifInterface.ORIENTATION_ROTATE_270:
matrix.postRotate(270);
break;
}
String filePath = getRealPathFromURI(uriFilePath);
file = new File(new URI("file://" + filePath.replace(" ", "%20")));//photo is file type that is global
Glide.with(this)
.load(file)
.placeholder(R.drawable.upload_image)
.into(dp);
// getImageDetails(photo);
} catch (Exception e) {
e.printStackTrace();
}
}
} else if (requestCode == REQUEST_PICK_IMAGE) {
if (resultCode == RESULT_OK) {
Uri selectedImageUri = data.getData();
String selectedImagePath = getRealPathFromURI(selectedImageUri);
Toast.makeText(this, selectedImagePath, Toast.LENGTH_SHORT).show();
try {
file = new File(new URI("file://" + selectedImagePath.replace(" ", "%20")));
Glide.with(this).load(file).placeholder(R.drawable.upload_image)
.into(dp);
} catch (URISyntaxException e) {
e.printStackTrace();
}
}
}
}
public String getRealPathFromURI(Uri uri) {
if (uri == null) {
return null;
}
String[] projection = {MediaStore.Images.Media.DATA};
Cursor cursor = this.getContentResolver().query(uri, projection, null, null, null);
if (cursor != null) {
cursor.moveToFirst();
int column_index = cursor.getColumnIndex(projection[0]);
return cursor.getString(column_index);
}
return uri.getPath();
}
public HashMap<String, String> getparams() { //parameters passed while hitting the API
HashMap<String, String> params = new HashMap<>();
params.put(rulee, "sign_up");
params.put(emaill, email.getText().toString());
params.put(word, password.getText().toString());
params.put(f_name, fullName.getText().toString());
params.put(n_p_a, selections.getText().toString());
params.put(or_name, orgName.getText().toString());
params.put(or_type, selectedOrgType);
Toast.makeText(this, selectedRole, Toast.LENGTH_SHORT).show();
params.put(rolId, selectedRole);
return params;
}
#Override
public void response(String responseObject, String method_call) //this gets the response when API is hit
{
progressDialog.dismissDialog();
try {
JSONObject response = new JSONObject(responseObject);
if (response.getString("flag").equalsIgnoreCase("success")) {
JSONObject object = response.getJSONObject("response");
sharedPreference_main.setUserName(object.getString(f_name));
sharedPreference_main.setUserEmail(object.getString(emaill));
sharedPreference_main.setUserOrganisation(object.getString(or_name));
sharedPreference_main.setUserRole(object.getString(rol));
sharedPreference_main.setOrgType(object.getString(or_type));
sharedPreference_main.setNPA(object.getString(n_p_a));
sharedPreference_main.setUserProfilePic(object.getString(prof_pic));
onSignupSuccess(); //if everything works out call the home activity
} else if (response.getString("flag").equalsIgnoreCase("0")) {
String resp = response.getString("response");
builder.setTitle("Error:"); //building up the dialog
builder.setMessage(resp);
displayAlert(resp);
} else if (response.getString("flag").equalsIgnoreCase("1")) {
// Toast.makeText(this, response.getString("flag"), Toast.LENGTH_SHORT).show();
JSONArray data = response.getJSONArray("message");
if (data.length() > 0) {
for (int i = 0; i < data.length(); i++) {
JSONObject inData = data.getJSONObject(i);
if (inData.has("role_name")) {
role_list.add(inData.getString("role_name"));
} else if (inData.has("organisation_type")) {
org_type.add(inData.getString("organisation_type"));
} else if (inData.has("prior_name")) {
nat_pri_area.add(inData.getString("prior_name"));
}
// N_P_A.add(inData.getString("prior_name"));
}
}
if (role_list.size() > 0) {
// String[] role = role_list.toArray(new String[role_list.size()]);
roleSpinner.setAdapter(adapterSetter(role_list));
}
if (org_type != null) {
// String organisationType[] =org_type.toArray(new String[org_type.size()]);
organisationTypeSpinner.setAdapter(adapterSetter(org_type));
}
// String[] priorityArea = org_type.toArray(new String[org_type.size()]);
//
}
// onSignupSuccess();
} catch (JSONException e) {
e.printStackTrace();
}
}
#Override
public void error(String error) {
progressDialog.dismissDialog();
Toast.makeText(this, error, Toast.LENGTH_SHORT).show();
}
private void displayAlert(final String code) {
builder.setPositiveButton("OK", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialogInterface, int i) {
fullName.setText("");
email.setText("");
password.setText("");
orgName.setText("");
}
}).show();
}
private void displayAlert() //overloaded function
{
builder.setTitle("No internet connection");
builder.setTitle("Please switch on the internet");
builder.setPositiveButton("Retry", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialogInterface, int i) {
// checkConnection();
if (receiver.isNetworkAvailable()) {
dialogInterface.c**strong text**ancel();
} else {
displayAlert();
}
}
}).setNegativeButton("Exit", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialogInterface, int i) {
// checkConnection();
dialogInterface.cancel();
}
}).show();
}
public void getData() {
GetServerData getServerData = new GetServerData(this);
getServerData.getRoles();
}
}
Note:
Language version - Java
Target SDK -23
Any help would be appreciated.
This was happening because the permissions were not being provided to the application while running it on the smartphone. Newer versions of Android require the apps to be granted permissions from within the smartphone.
Use this and upvote after your issue gets resolve.
private File profilePic;
private Uri photoFileUri;
/**
* Method below will work for Camera Intent.
*/
private void clickPicture() {
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
if (takePictureIntent.resolveActivity(getPackageManager()) != null) {
try {
photoFile = AppUtils.getInstance().createImageFile(); // Create the File where the photo should go
outputFileUri = FileProvider.getUriForFile(SignUpActivity.this, getApplicationContext().getPackageName() + ".provider", photoFile);
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, outputFileUri);
startActivityForResult(takePictureIntent, CAMERA_IMAGE_REQUEST);
} catch (IOException io) {
io.printStackTrace(); // Error occurred while creating the File
}
//outputFileUri = Uri.fromFile(photoFile);//At this Uri the image captured will get saved.
}
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if (resultCode == Activity.RESULT_OK) {
switch (requestCode) {
case AppConstants.MediaConstants.REQUEST_CAPTURE_IMAGE:
profilePic = new File(AppUtils.getInstance().getRealPathFromURI(photoFileUri, mActivity));
break;
}
}
}
Use this method below directly in your classs
/**
* method to get real path from uri
*
* #param contentURI
* #param context
* #return
*/
public String getRealPathFromURI(Uri contentURI, Context context) {
String result;
Cursor cursor = context.getContentResolver().query(contentURI, null, null, null, null);
if (cursor == null) { // Source is Dropbox or other similar local file path
result = contentURI.getPath();
} else {
cursor.moveToFirst();
int idx = cursor.getColumnIndex(MediaStore.Images.ImageColumns.DATA);
result = cursor.getString(idx);
cursor.close();
}
return result;
}
create "provide_paths.xml" file in folder name "xml" in res directory and add code below in it
<?xml version="1.0" encoding="utf-8"?>
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<external-path
name="external_files"
path="." />
</paths>
I am using a contact picker to get the number to an editText. The saved contact numbers can be of three types based on how the user saved a particular number.
+911234567899 (with +91 as prefix) [India CountryCode].
01234567899 (with 0 as prefix) [Common STD Code used to call mobile numbers].
1234567899 (without any prefix).
I need to get remove the prefixes (if any) and get the actual 10 digit number without spaces to my editText (some devices put spaces between the numbers for better readability).
Now the issue I am facing is, this works perfect only for the first time you pick each type of contact, Like, It will work for the 1st time you pick a prefixed number and non prefixed number. The next time you try it, it won't work as i need. But works again perfect if we restart the app.
This is the code:
ScreenMain.java
import android.Manifest;
import android.content.ActivityNotFoundException;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.graphics.Color;
import android.net.Uri;
import android.provider.ContactsContract;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.support.v4.view.accessibility.AccessibilityNodeInfoCompat;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.MotionEvent;
import android.view.View;
import android.view.WindowManager;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageButton;
import android.widget.ImageView;
import android.widget.TextView;
import android.widget.Toast;
public class ScreenMain extends AppCompatActivity {
private static final int PERMISSION_ALL = 1;
ImageButton btnGetNumber;
EditText etMobileNumber;
private String sMobileNumber = "";
private Uri uriContact;
private String contactID; // contacts unique ID
private static ScreenMain inst;
public static ScreenMain instance() {
return inst;
}
#Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_screen_main);
btnGetData = (Button) findViewById(R.id.btndGetStatus);
etMobileNumber = (EditText) findViewById(R.id.etdMobileNumber);
String[] PERMISSIONS = { Manifest.permission.READ_CONTACTS,
Manifest.permission.WRITE_CONTACTS,
};
ActivityCompat.requestPermissions(this, PERMISSIONS, PERMISSION_ALL);
etMobileNumber.setOnClickListener(new View.OnClickListener()
{
public void onClick(View view)
{
getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_PAN);
}
});
btnGetNumber.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
// using native contacts selection
// Intent.ACTION_PICK = Pick an item from the data, returning what was selected.
startActivityForResult(new Intent(Intent.ACTION_PICK, ContactsContract.Contacts.CONTENT_URI), REQUEST_CODE_PICK_CONTACTS);
}
});
btnGetData.setOnClickListener(new View.OnClickListener() {
public void onClick(View view) {
// sendSms("mONST");
ClassSMS.sendSms(getApplicationContext(),"mONST",etMobileNumber.getText().toString());
}
});
btnCall.setOnClickListener(new View.OnClickListener() {
public void onClick(View view) {
// ClassMakeCall.makeCall(getApplicationContext(),etMobileNumber.getText().toString());
String ssMobNumber = etMobileNumber.getText().toString();
if (ssMobNumber.length() == 0) {
Toast.makeText(getApplicationContext(), " Please enter mobile number in the motorON unit", Toast.LENGTH_SHORT).show();
return;
}
if (ssMobNumber.length() != 10) {
Toast.makeText(getApplicationContext(), " Invalid mobile number", Toast.LENGTH_SHORT).show();
return;
}
try {
Intent callIntent = new Intent(Intent.ACTION_CALL);
callIntent.setData(Uri.parse("tel:+91" + ssMobNumber));
if (ActivityCompat.checkSelfPermission(getApplicationContext(), Manifest.permission.CALL_PHONE) != PackageManager.PERMISSION_GRANTED) {
// TODO: Consider calling
// ActivityCompat#requestPermissions
// here to request the missing permissions, and then overriding
// public void onRequestPermissionsResult(int requestCode, String[] permissions,
// int[] grantResults)
// to handle the case where the user grants the permission. See the documentation
// for ActivityCompat#requestPermissions for more details.
Toast.makeText(getApplicationContext()," SMS Fail, Please goto Settings -> APPS -> motorON -> Permissions and enable SMS permission ", Toast.LENGTH_SHORT).show();
return;
}
startActivity(callIntent);
} catch (ActivityNotFoundException activityException) {
Toast.makeText(getApplicationContext()," unable to make call", Toast.LENGTH_SHORT).show();
}
}
});
ivSettings.setOnClickListener( new View.OnClickListener() {
#Override
public void onClick(View v) {
startActivity(new Intent(getApplicationContext(), ScreenSettings.class));
}
});
}
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == REQUEST_CODE_PICK_CONTACTS && resultCode == RESULT_OK) {
// Log.d(TAG, "Response: " + data.toString());
uriContact = data.getData();
ClassGetPhoneNumber.retrieveContactNumber(getApplicationContext(),uriContact);
if(ClassGetPhoneNumber.sStatus.equals("OK"))
{
etMobileNumber.setText(ClassGetPhoneNumber.sResponse);
}
}
}
#Override
protected void onStart() {
super.onStart();
inst = this;
getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_PAN);
}
#Override
protected void onRestart(){
super.onRestart();
getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_PAN);
// Log.d(TAG, "atvt restart");
}
#Override
protected void onResume(){
super.onResume();
getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_PAN);
// Log.d(TAG, "atvt resume");
}
#Override
protected void onPause(){
super.onPause();
// Log.d(TAG, "atvt pause");
}
#Override
protected void onStop(){
super.onStop();
// Log.d(TAG, "atvt stop");
}
#Override
protected void onDestroy()
{
super.onDestroy();
// Log.d(TAG, "atvt destroy");
}
#Override
public void onRequestPermissionsResult(int requestCode,
String permissions[], int[] grantResults)
{
switch (requestCode)
{
case PERMISSION_ALL:
{
// If request is cancelled, the result arrays are empty.
if (grantResults.length > 0
&& grantResults[0] == PackageManager.PERMISSION_GRANTED)
{
}
else
{
Toast.makeText(getApplicationContext()," App Needs SMS Permission to Work ", Toast.LENGTH_SHORT).show();
}
return;
}
}
}
}
ClassGetPhoneNumber.java
import android.content.Context;
import android.database.Cursor;
import android.net.Uri;
import android.provider.ContactsContract;
import android.util.Log;
class ClassGetPhoneNumber
{
private static final String TAG = null ;
public static String sStatus="ERROR";
public static String sResponse;
public static String sContactNumber;
public static String sContactNumberFinal;
public static int With91 = 0, With0 = 0, TenDigit = 0, InvalidNumber = 0;
public static String contactID=""; // contacts unique ID
public static String contactNumber = null;
public static void retrieveContactNumber(Context context, Uri uriContact)
{
// getting contacts ID
Cursor cursorID = context.getContentResolver().query(uriContact,
new String[]{ContactsContract.Contacts._ID},
null, null, null);
if (cursorID.moveToFirst()) {
contactID = cursorID.getString(cursorID.getColumnIndex(ContactsContract.Contacts._ID));
}
cursorID.close();
// Using the contact ID now we will get contact phone number
Cursor cursorPhone = context.getContentResolver().query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI,
new String[]{ContactsContract.CommonDataKinds.Phone.NUMBER},
ContactsContract.CommonDataKinds.Phone.CONTACT_ID + " = ? AND " +
ContactsContract.CommonDataKinds.Phone.TYPE + " = " +
ContactsContract.CommonDataKinds.Phone.TYPE_MOBILE,
new String[]{contactID},
null);
contactNumber = null;
if (cursorPhone.moveToFirst()) {
contactNumber = cursorPhone.getString(cursorPhone.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
}
cursorPhone.close();
sResponse = null;
sContactNumber = null;
sContactNumberFinal = null;
sContactNumber = contactNumber.replaceAll("\\s","");
int iLength = sContactNumber.length();
if(iLength==13)
With91 = 1;
if(iLength==11)
With0 = 1;
if(iLength==10)
TenDigit = 1;
if(With91 == 1)
{
sContactNumberFinal = sContactNumber.substring(3);
Log.e(TAG,"In With91, sContactNumberFinal : "+sContactNumberFinal);
sResponse = sContactNumberFinal;
sStatus = "OK";
}
if (With0 == 1)
{
sContactNumberFinal = sContactNumber.substring(1);
Log.e(TAG,"In With0, sContactNumberFinal : "+sContactNumberFinal);
sResponse = sContactNumberFinal;
sStatus = "OK";
}
if (TenDigit == 1)
{
sContactNumberFinal = sContactNumber;
Log.e(TAG,"In TenDigit, sContactNumberFinal : "+sContactNumberFinal);
sResponse = sContactNumberFinal;
sStatus = "OK";
}
}
}
I agree with #DaveyDaveDave static fields are not the way to go, but if you insist here's your same code, with lots of fixes and simplified code.
Note that NORMALIZED_NUMBER is only supported from API 16 and above.
class ClassGetPhoneNumber {
...
public static void retrieveContactNumber(Context context, Uri uriContact) {
sResponse = null;
sContactNumber = null;
sContactNumberFinal = null;
// get contactID from contactUri
long contactID = ContentUris.parseId(contactUri);
// Using the contact ID now we will get contact phone number
// Don't add selection by Phone.TYPE as we might miss a lot of phones.
// We ask for the normalized number, this will only work for API 16 and above
Cursor cursorPhone = context.getContentResolver().query(CommonDataKinds.Phone.CONTENT_URI,
new String[]{CommonDataKinds.Phone.NORMALIZED_NUMBER, CommonDataKinds.Phone.NUMBER},
CommonDataKinds.Phone.CONTACT_ID + " = " + contactID,null,null);
contactNumber = null;
if (cursorPhone != null && cursorPhone.moveToFirst()) {
contactNumber = cursorPhone.getString(0); // this number will always be of e164 format: "+<country><local number>"
Log.d(TAG, "normalized number: " + contactNumber + ", original number: " + cursorPhone.getString(1) + ", contact-id: " + contactID);
} else {
// you need to quit here, otherwise you'll be using an old value of contactNumber in the rest of the code.
if (cursorPhone != null) {
cursorPhone.close();
}
return;
}
cursorPhone.close();
if (!TextUtils.isEmpty(contactNumber)) {
sContactNumber = contactNumber;
sContactNumberFinal = sContactNumber.substring(3);
sResponse = sContactNumberFinal;
sStatus = "OK";
} else {
// no phone was found
sStatus = "NOT FOUND";
}
}
}
It's hard to follow your code, because there's an awful lot going on, but I think the root cause will be that everything in your ClassGetPhoneNumber class is static, so the fields in that class are set on the first pass, and their values remain the next time you call the retrieveContactNumber method.
From looking at it, I suspect it's not as simple as it working the first time and not working subsequently, but rather that you get generally 'odd' behaviour, depending on the input.
The simplest solution would be to remove all the static keywords from the ClassGetPhoneNumber class, and to change the call from:
ClassGetPhoneNumber.retrieveContactNumber(getApplicationContext(),uriContact);
to:
new ClassGetPhoneNumber().retrieveContactNumber(getApplicationContext(),uriContact);
I think that will resolve the immediate problems you have.
I figured it out.
The issue was:
The value of the variables which I used to determine how the user has saved a
particular number (With91, With0, TenDigit), was not initialized to zero at the start of the
retrieveContactNumber() method.
Initializing them to zero at the start of the function cleared its previous
values and made it work as intended.
Thanks everyone for your time and support.
-Paul Varghese
I am creating an android camera app using opencv. First I make it like when I click the start button, it start taking pictures and in every second takes a picture and store it in storage. It works perfectly for me.
Then I tried to make it some tricky by forcing it to take 5 pictures in a second it works well.
But actually I faced problem when I make it to 20 pictures in 1 second. It did not work. The app hangs as soon as I click on the start button. I don't know why. But I think the problem is in threading.
Can someone help me how i will do it.
I have two java files in my project and here is the code.
package org.opencv.samples.tutorial3;
import java.io.FileOutputStream;
import java.util.List;
import org.opencv.android.JavaCameraView;
import android.content.Context;
import android.hardware.Camera;
import android.hardware.Camera.PictureCallback;
import android.hardware.Camera.Size;
import android.util.AttributeSet;
import android.util.Log;
public class Tutorial3View extends JavaCameraView implements PictureCallback {
private static final String TAG = "Sample::Tutorial3View";
private String mPictureFileName;
public Tutorial3View(Context context, AttributeSet attrs) {
super(context, attrs);
}
public List<String> getEffectList() {
return mCamera.getParameters().getSupportedColorEffects();
}
public boolean isEffectSupported() {
return (mCamera.getParameters().getColorEffect() != null);
}
public String getEffect() {
return mCamera.getParameters().getColorEffect();
}
public void setEffect(String effect) {
Camera.Parameters params = mCamera.getParameters();
params.setColorEffect(effect);
mCamera.setParameters(params);
}
public List<Size> getResolutionList() {
return mCamera.getParameters().getSupportedPreviewSizes();
}
public void setResolution(Size resolution) {
disconnectCamera();
mMaxHeight = resolution.height;
mMaxWidth = resolution.width;
connectCamera(getWidth(), getHeight());
}
public Size getResolution() {
return mCamera.getParameters().getPreviewSize();
}
public void takePicture(final String fileName) {
Log.i(TAG, "Taking picture");
this.mPictureFileName = fileName;
// Postview and jpeg are sent in the same buffers if the queue is not empty when performing a capture.
// Clear up buffers to avoid mCamera.takePicture to be stuck because of a memory issue
mCamera.setPreviewCallback(null);
// PictureCallback is implemented by the current class
mCamera.takePicture(null, null, this);
}
#Override
public void onPictureTaken(byte[] data, Camera camera) {
Log.i(TAG, "Saving a bitmap to file");
// The camera preview was automatically stopped. Start it again.
mCamera.startPreview();
mCamera.setPreviewCallback(this);
// Write the image in a file (in jpeg format)
try {
FileOutputStream fos = new FileOutputStream(mPictureFileName);
fos.write(data);
fos.close();
} catch (java.io.IOException e) {
Log.e("PictureDemo", "Exception in photoCallback", e);
}
}
}
And the second one is:
package org.opencv.samples.tutorial3;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.ListIterator;
import org.opencv.android.BaseLoaderCallback;
import org.opencv.android.CameraBridgeViewBase.CvCameraViewFrame;
import org.opencv.android.LoaderCallbackInterface;
import org.opencv.android.OpenCVLoader;
import org.opencv.core.Mat;
import org.opencv.android.CameraBridgeViewBase.CvCameraViewListener2;
import android.annotation.SuppressLint;
import android.app.Activity;
import android.hardware.Camera.Size;
import android.os.Bundle;
import android.os.Environment;
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.view.MotionEvent;
import android.view.SubMenu;
import android.view.SurfaceView;
import android.view.View;
import android.view.View.OnTouchListener;
import android.view.WindowManager;
import android.widget.Button;
import android.widget.Toast;
public class Tutorial3Activity extends Activity implements CvCameraViewListener2 {
private static final String TAG = "OCVSample::Activity";
private Tutorial3View mOpenCvCameraView;
private List<Size> mResolutionList;
private MenuItem[] mEffectMenuItems;
private SubMenu mColorEffectsMenu;
private MenuItem[] mResolutionMenuItems;
private SubMenu mResolutionMenu;
Thread thread;
Button start,stop;
boolean loop=false;
private BaseLoaderCallback mLoaderCallback = new BaseLoaderCallback(this) {
#Override
public void onManagerConnected(int status) {
switch (status) {
case LoaderCallbackInterface.SUCCESS:
{
Log.i(TAG, "OpenCV loaded successfully");
mOpenCvCameraView.enableView();
} break;
default:
{
super.onManagerConnected(status);
} break;
}
}
};
public Tutorial3Activity() {
Log.i(TAG, "Instantiated new " + this.getClass());
}
/** Called when the activity is first created. */
#Override
public void onCreate(Bundle savedInstanceState) {
Log.i(TAG, "called onCreate");
super.onCreate(savedInstanceState);
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
setContentView(R.layout.tutorial3_surface_view);
start=(Button)findViewById(R.id.button2) ;
start.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
loop=true;
thread = new Thread(new task());
thread.start();
}
});
stop=(Button) findViewById(R.id.button);
stop.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
loop=false;
}
});
mOpenCvCameraView = (Tutorial3View) findViewById(R.id.tutorial3_activity_java_surface_view);
mOpenCvCameraView.setVisibility(SurfaceView.VISIBLE);
mOpenCvCameraView.setCvCameraViewListener(this);
}
#Override
public void onPause()
{
super.onPause();
if (mOpenCvCameraView != null)
mOpenCvCameraView.disableView();
}
#Override
public void onResume()
{
super.onResume();
if (!OpenCVLoader.initDebug()) {
Log.d(TAG, "Internal OpenCV library not found. Using OpenCV Manager for initialization");
OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_3_0_0, this, mLoaderCallback);
} else {
Log.d(TAG, "OpenCV library found inside package. Using it!");
mLoaderCallback.onManagerConnected(LoaderCallbackInterface.SUCCESS);
}
}
public void onDestroy() {
super.onDestroy();
if (mOpenCvCameraView != null)
mOpenCvCameraView.disableView();
}
public void onCameraViewStarted(int width, int height) {
}
public void onCameraViewStopped() {
}
public Mat onCameraFrame(CvCameraViewFrame inputFrame) {
return inputFrame.rgba();
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
List<String> effects = mOpenCvCameraView.getEffectList();
if (effects == null) {
Log.e(TAG, "Color effects are not supported by device!");
return true;
}
mColorEffectsMenu = menu.addSubMenu("Color Effect");
mEffectMenuItems = new MenuItem[effects.size()];
int idx = 0;
ListIterator<String> effectItr = effects.listIterator();
while(effectItr.hasNext()) {
String element = effectItr.next();
mEffectMenuItems[idx] = mColorEffectsMenu.add(1, idx, Menu.NONE, element);
idx++;
}
mResolutionMenu = menu.addSubMenu("Resolution");
mResolutionList = mOpenCvCameraView.getResolutionList();
mResolutionMenuItems = new MenuItem[mResolutionList.size()];
ListIterator<Size> resolutionItr = mResolutionList.listIterator();
idx = 0;
while(resolutionItr.hasNext()) {
Size element = resolutionItr.next();
mResolutionMenuItems[idx] = mResolutionMenu.add(2, idx, Menu.NONE,
Integer.valueOf(element.width).toString() + "x" + Integer.valueOf(element.height).toString());
idx++;
}
return true;
}
public boolean onOptionsItemSelected(MenuItem item) {
Log.i(TAG, "called onOptionsItemSelected; selected item: " + item);
if (item.getGroupId() == 1)
{
mOpenCvCameraView.setEffect((String) item.getTitle());
Toast.makeText(this, mOpenCvCameraView.getEffect(), Toast.LENGTH_SHORT).show();
}
else if (item.getGroupId() == 2)
{
int id = item.getItemId();
Size resolution = mResolutionList.get(id);
mOpenCvCameraView.setResolution(resolution);
resolution = mOpenCvCameraView.getResolution();
String caption = Integer.valueOf(resolution.width).toString() + "x" + Integer.valueOf(resolution.height).toString();
Toast.makeText(this, caption, Toast.LENGTH_SHORT).show();
}
return true;
}
class task implements Runnable {
public void run() {
while (loop) {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd_HH-mm-ss");
String currentDateandTime = sdf.format(new Date());
final String fileName = Environment.getExternalStorageDirectory().getPath() +
"/sample_picture_" + currentDateandTime + ".jpg";
mOpenCvCameraView.takePicture(fileName);
runOnUiThread(new Runnable() {
#Override
public void run() {
Toast.makeText(Tutorial3Activity.this, fileName + " saved", Toast.LENGTH_SHORT).show();
}
});
try {
thread.sleep(200);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
}
Note: The above code works well for taking 5 pictures in 1 second. But when I change thread.sleep(200) to thread.sleep(50) for taking 20 pictures in 1 second it hangs.