first question here!
I am interested in acquiring raw GPS data on android devices: satellite positions, pseudoranges, and phase information. According to this well-answered question, the best we can do is get everything that GpsSatellite provides.
I'm wondering if the situation has changed in the past five years? I noticed that the Android source now a structure named GpsMeasurement, which sounds like it has everything I want in it, and is used similar to the well-known GpsStatus structure.
However, GpsMeasurement is #SystemApi and thus not accessible via normal app writing. Further, I can't find any information on this beyond source code.
Is there not another way to get this data? Is there a workaround to access GpsMeasurement regardless? There's really nothing in there that should be kept from developers.
So looks like this has changed recently. Here is a link describing how to get the raw GPS data off of modern smartphones: Raw GNSS Measurements
I doubt that you ever will have access to that data on an consumer android handy.
The reason is, that the GPS chip has to specially configured to output these pseudo ranges, this produces overhead that normally nobody uses.
Further GPS chips that are able to output pseudeoranges, are often more expensive.
This is called the "raw-data option".
Related
How can one of our many users get
java.lang.NoSuchMethodError:
at com.mycelium.wallet.activity.settings.SettingsPreference.getLanguage (SettingsPreference.kt:73)
at com.mycelium.wallet.WalletApplication.onCreate (WalletApplication.java:109)
at android.app.Instrumentation.callApplicationOnCreate (Instrumentation.java:1127)
on this line of Kotlin code:
#JvmStatic
fun getLanguage(): String? = sharedPreferences.getString(Constants.LANGUAGE_SETTING, Locale.getDefault().language)
There are three function calls on this line: android.content.SharedPreferences::getString(String,String), java.util.Locale::getDefault() and java.util.Locale::getLanguage() all of which are available since API 1.
The only affected user (Samsung Galaxy A5(2017) (a5y17lte), 2816MB RAM, Android 8.0) tried to start the app 180 times with this insta-crash.
The conversion to Kotlin might have issues still?
try { ... } catch (NoSuchMethodError e) { ... } might be a suitable workaround. But they already might have given up; if you don't have any email address or alike, you won't be able to notify them. You'd could return a static string in case of a NoSuchMethodError. Besides, if one has written down the seed phrase, the wallet is on the block-chain, the device only has the keys. I'd file that as an individual destiny - and that device probably could still be rooted, to have the keys extracted. It's difficult to help them without having a support request, so that one could notify them of a new version, which not relies on whatever unknown method. Maybe they still use it and would receive an auto-update and try again, but only maybe - but there's no guarantee, that this is the only one unknown method on this device.
It's definitely not a Kotlin issue, but rather a storage defect; google "eMMC corruption".
And if the user has not written down their seed phrase, it's their very own fault.
This all is an assumption, but the probability isn't that low.
As you know (I am sure) a NoSuchMethodError is caused by a mismatch between the versions of classes at compile time versus at runtime.
And, I agree with you that the three methods called by that line of code should be present at runtime.
I was a suspicious that there isn't a message string for the NoSuchMethodError to say which method was missing, but there are other examples for the Android platform where the message is missing. So I am (tentatively) calling this not significant.
So we have to look for other explanations. Here are some:
The line number in the stacktrace could be inaccurate. People sometimes report this kind of thing; e.g. Crashlytics is reporting wrong line numbers
This particular user could be running a different (older?) version of your app where the code at that line is different to code you are looking at.
The user has "rooted" his device and messed around with its standard libraries. Alternatively, the user's device has been hacked and the hacker has interfered with the standard libraries (rather crudely in this case).
The user has been messing with the bytecodes for your app and has accidentally got it trying to call a non-existent method. Alternatively, the user is running a (crudely) trojaned version of your app where the bad guy has done the same thing.
The fact that your app involves Bitcoins means that there could be strong incentive for someone to be doing nefarious things ... so the last two alternatives should not be discounted.
The conversion to Kotlin might have issues still?
I don't see why that would affect only one user.
The fact the user tried 180 times is why I care. This is a Bitcoin wallet, so ... they might have money in that wallet and I hate to not fix issues if I can.
(Or conversely, this might be a bad guy trying to get bitcoins out of a wallet via a stolen device. The fact that the user is being so persistent ... and hasn't contacted you for help ... is suspicious in itself.)
But the point is that if you don't have any way to contact this user, fixing the issue in general is unlikely to help them directly. And right now you don't have enough information to know what the problem really is.
I have a found a free API to get some data I need for my app. The thing is the values that I get are in English.
I wanted to know if there is some way to translate this strings in my language before showing them to the users.
You can translate text but it will require another API call. Not only that, but you will have to create an appropriate request object and parse a response object from your chosen API.
You have various API providers to choose from, the top Google hits being:
Google: https://cloud.google.com/translate/
Yandex: https://tech.yandex.com/translate/
But beware! Machine translation is patchy at best. The likelihood of getting odd sounding or outright wrong results, particularly for anything other than simple text, is very high.
Here's the situation:
I get two VCards from our web-service and I have to share them via email (or any other suitable channel - not really relevant).
I could save them to files, and then send URIs to the intent using putParcelableArrayListExtra, but I'd really like not to use storage, because I'd rather not nag user with storage permissions just because of this.
I did see this solution, which looks like it does what I need to do (haven't tried it, yet). However, is there any cleaner way of achieving this?
Since there is limited amount of fields on the VCard (about 10), would it be okay to just make Parcelable object of my own, copy fields from received VCard and share it as text/x-vcard using putParcelableArrayListExtra?
I'd like someone to just steer me in the right direction, since I'm quite lost right now.
As Selvin said in the comment:
FileProvider is the answer ... you can share your app private file(so you don't need storage permissions) with other apps using it ... you may also use ContentProvider directly if you wana provide this information from memory/database directly
I wanted to learn more about the Android Services / Broadcasts, so I started a simple project, to create a battery monitoring app. It turned out pretty good, I'm using it for a few days now, but I want to add a new function: to show since when is the phone charging/discharging.
First I thought that I would create two static fields in my BoradcastReciever extension class, where I get and publish the data about the battery, one for the actual state (charging/discharging), and one for the time, when the change in state happened. This way, I could just subtract from the current time the last change, and know exactly since when is the phone charging/discharging.
But there is a problem with this solution: It won't show the correct data at first, when a user starts the app. I wouldn't make a big deal of it, but I saw that Android tracks this data somewhere, because inside my phone settings I found this information, so why take the hard way.
So my question is: is there an easy way to get from the Android system the date/time (no matter what format) of the last charging state change?
I looked at the BatteryManager reference but there are no constants named after what I seek, and which I could use, to get the information from the Intent of my receiver.
The Android OS tracks the connect/disconnect of a power source, but does not make this data accessible to apps. You have to record this all yourself, using intent filters.
The two intent filters to use are android.intent.action.ACTION_POWER_CONNECTED and android.intent.action.ACTION_POWER_DISCONNECTED; with these, you can monitor when the power source is connected and disconnected.
You can find information about this process explained incredibly clearly here. Another blog describing the process can be found here.
I want to write a program that will be able to call into my company's bi-weekly conference calls, and record the call, so it can then be made into a podcast.
I am thinking of using Gizmo's SIP interface (and the fact that it allows you to make toll-free calls for free), but I am having trouble finding any example code (preferably in Java) that will be able to make an audio call, and get hold of the audio stream.
I have seen plenty of SIP programming tutorials that deal with establishing a session, and then they seem to just do some hand waving, and say "here is where you can establish the audio connection" without actually doing it.
I am experienced in Java, so I would prefer to use it, but other language suggestions are welcome as well.
I have never written a VOIP application, so I'm not really sure where to start. Can anyone suggest a good library or other resource that would help me get started?
Thanks!
Look for a VOIP softphone writtin in Java, then modify it to save the final audio stream instead of sending it to be played.
Side note: In many states you would be violating the law unless you do one of several things, varying by state: Notify the participants they're being recorded, insert BEEPs every N seconds, both, etc. Probably you only have to comply with the laws of the state you're calling from. Even worse, you may need to allow the users to decline recording (requires you to be there before recording starts). If you control the conference server, you may be able to get it to play a canned announcement that the call is being recorded.
You could do this with Twilio with almost no programming whatsoever. It will cost you 3ยข per minute, so if your company's weekly call is 45 minutes long, you're looking at $1.35 per week, about as close to free as possible. Here are the steps:
Sign up for Twilio and make note of your Account ID and token
Create a publicly accessible file on your web server that does nothing but output the following XML (see the documentation for explanation of the record parameters):
<Response>
<Record timeout="30" finishOnKey="#" />
</ Response>
When it's time to start the recording, perform a POST to this URL (documented here) with your browser or set up an automated process or script to do it for you:
POST http://api.twilio.com/2008-08-01/Accounts/ACCOUNT SID HERE/Calls
HTTP/1.1
Called=CONFERENCE NUMBER HERE
&Url=WEB PAGE HERE
&Method=GET
&SendDigits=PIN CODE HERE
If you want to get really creative, you can actually write code to handle the result of the recording verb and email the link to the MP3 or WAV file that Twilio hosts for you. But, if this is a one off, you can skip it because you can access all your recordings in the control panel for your account anyway.
try peers with mediaDebug option true in peers.xml. This option records all outgoing and incoming media streams in a media/ folder with a date pattern for file name. Nevertheless this file will probably not be usable as is. It contains raw uncompressed lienar PCM samples. You can use Audacity, sox or ffmpeg to convert it to whatever you want.
https://voip.dev.java.net/
They have some sample code there.