tag:blogger.com,1999:blog-898787495633912122024-03-14T00:13:04.185-07:00Android-er<i>Please visit my new address:</i> <b><a href="https://coxxect.blogspot.com/">https://coxxect.blogspot.com/</a></b>Unknownnoreply@blogger.comBlogger2365125tag:blogger.com,1999:blog-89878749563391212.post-84051687016995349622022-05-22T13:51:00.002-07:002022-05-22T13:51:30.716-07:00Simplest Snackbar <p>
<i><b><a href="https://developer.android.com/reference/com/google/android/material/snackbar/Snackbar" target="_blank">Snackbars</a></b>
provide lightweight feedback about an operation. They show a brief message
at the bottom of the screen on mobile and lower left on larger devices.
Snackbars appear above all other elements on screen and only one can be
displayed at a time.<br /><br />They automatically disappear after a timeout
or after user interaction elsewhere on the screen, particularly after
interactions that summon a new surface or activity. Snackbars can be swiped
off screen.</i><br /><br />It's a simplest example to show Snackbar using Kotlin. The
layout xml is same as last post "<a href="https://android-er.blogspot.com/2022/05/simple-example-of-button-and-toast.html">Simple example of Button and Toast</a>".
</p>
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiL9MqdGow7TKQeJAda2AlO5eyRFQOCceIoy_-CQ57xo5pfk8it1AevTTVPQDWcMdp_Z7KfBFPUm1Y-C06301lnYUb5WdNe8_yI-ZqU_8BjGFgSeb3zq_vrx4LTmTAXd_MJwe8Iis1f5pFCz19LxU0QWXW-0IPP5tKTF34AWsQzXa9yxrYcKCKTTmtR/s1366/Snackbar.png" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="768" data-original-width="1366" height="180" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiL9MqdGow7TKQeJAda2AlO5eyRFQOCceIoy_-CQ57xo5pfk8it1AevTTVPQDWcMdp_Z7KfBFPUm1Y-C06301lnYUb5WdNe8_yI-ZqU_8BjGFgSeb3zq_vrx4LTmTAXd_MJwe8Iis1f5pFCz19LxU0QWXW-0IPP5tKTF34AWsQzXa9yxrYcKCKTTmtR/s320/Snackbar.png" width="320" /></a>
</div>
<br />
MainActivity.kt
<pre style="border: 1px solid black;"><code><span style="color: black;">package android_er.blogspot.com.myapp01
import android.os.Bundle
import android.view.View
import android.widget.Button
import android.widget.Toast
import androidx.appcompat.app.AppCompatActivity
import com.google.android.material.snackbar.Snackbar
private lateinit var btnA: Button
private lateinit var btnB: Button
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
btnA = findViewById(R.id.btn_A)
btnB = findViewById(R.id.btn_B)
btnA.setOnClickListener(
{ view: View ->
Toast.makeText(
this,
"Button A pressed",
Toast.LENGTH_LONG,
).show()
},
)
btnB.setOnClickListener(
{ view: View ->
</span><span style="color: red;">val snackbar = Snackbar
.make(btnB,
"android-er.blogspot.com",
Snackbar.LENGTH_LONG)
snackbar.show()</span><span style="color: black;">
},
)
}
}
</span></code></pre>
<br />
Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-9576137827482459872022-05-22T12:37:00.003-07:002022-05-22T12:37:51.627-07:00Simple example of Button and Toast (Android Kotlin)<div class="separator" style="clear: both; text-align: center;"><a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjBxTDoPPVEuaSulh4P99fe-axnuVpCSjbyTZGAIlQ6EhR8zxNHFXC05wZoX_zqEVTuyxUJXnXwdFNwhOojRmUGwO7AEaDOQIq3SwHi-fsd6Lx5M5xw8kooPaFtSd1StNNxS_J9rT6PujTu4OCnVM5vYr48q6yNL-pqWgKOE4ecyAEncYkTIhuYBALM/s1366/button%20and%20Toast.png" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="768" data-original-width="1366" height="180" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjBxTDoPPVEuaSulh4P99fe-axnuVpCSjbyTZGAIlQ6EhR8zxNHFXC05wZoX_zqEVTuyxUJXnXwdFNwhOojRmUGwO7AEaDOQIq3SwHi-fsd6Lx5M5xw8kooPaFtSd1StNNxS_J9rT6PujTu4OCnVM5vYr48q6yNL-pqWgKOE4ecyAEncYkTIhuYBALM/s320/button%20and%20Toast.png" width="320" /></a>
</div>
<br />
activity_main.xml
<pre style="border: 1px solid black;"><code><span style="color: black;"><?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.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"
tools:context=".MainActivity">
</span><span style="color: red;"><LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
android:layout_margin="10dp">
<Button
android:id="@+id/btn_A"
android:layout_width="wrap_content"
android:layout_weight="1"
android:layout_height="wrap_content"
android:text="Button A"
android:layout_margin="5dp"/>
<Button
android:id="@+id/btn_B"
android:layout_width="wrap_content"
android:layout_weight="1"
android:layout_height="wrap_content"
android:text="Button B"
android:layout_margin="5dp"/>
</LinearLayout></span><span style="color: black;">
</androidx.constraintlayout.widget.ConstraintLayout>
</span></code></pre>
<br />
MainActivity.kt
<pre style="border: 1px solid black;"><code><span style="color: black;">package android_er.blogspot.com.myapp01
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.view.View
import android.widget.Button
import android.widget.Toast
</span><span style="color: red;">private lateinit var btnA: Button
private lateinit var btnB: Button</span><span style="color: black;">
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
</span><span style="color: red;">btnA = findViewById(R.id.btn_A)
btnB = findViewById(R.id.btn_B)
btnA.setOnClickListener(
{ view: View ->
Toast.makeText(
this,
"Button A pressed",
Toast.LENGTH_LONG,
).show()
},
)
btnB.setOnClickListener(
{ view: View ->
Toast.makeText(
this,
"Button B pressed",
Toast.LENGTH_LONG,
).show()
},
)</span><span style="color: black;">
}
}
</span></code></pre>
<br />Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-11630528886972997732021-06-14T08:56:00.006-07:002021-06-14T09:05:05.102-07:00TextInputLayout + TextInputEditText<p>
Simple example to
use com.google.android.material.textfield.TextInputLayout
and com.google.android.material.textfield.TextInputEditText in layout xml
to make edit text better.
</p>
<div class="separator" style="clear: both; text-align: center;"><a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEgYGjpJ5ogCr2TxmULi271qbwdna6xlbgaUHDAE1R4GyA6jftKBtTaOMwDtK0EWbS6crSkJxjqedHCqyhow5zIjdswn_t8MXhWr-FtScPZug_xzkjI0idQZ5NuqM0R4nOsbf1Pq2jBF1_Q/s1300/ExEditText.png" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="1300" data-original-width="750" height="400" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEgYGjpJ5ogCr2TxmULi271qbwdna6xlbgaUHDAE1R4GyA6jftKBtTaOMwDtK0EWbS6crSkJxjqedHCqyhow5zIjdswn_t8MXhWr-FtScPZug_xzkjI0idQZ5NuqM0R4nOsbf1Pq2jBF1_Q/w231-h400/ExEditText.png" width="231" /></a></div><div class="separator" style="clear: both; text-align: center;"><br /></div>
<pre style="border: 1px solid black;"><code><span style="color: black;"><?xml version="1.0" encoding="utf-8"?>
<LinearLayout
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"
tools:context=".MainActivity">
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="android-er.blogspot.com"
android:gravity="center"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Normal TextView"/>
<EditText
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="hint"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="TextInputLayout + TextInputEditText"/>
</span><span style="color: red;"><b><com.google.android.material.textfield.TextInputLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="Hint">
<com.google.android.material.textfield.TextInputEditText
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textStyle="bold"/>
</com.google.android.material.textfield.TextInputLayout></b></span><span style="color: black;">
</LinearLayout>
</span></code></pre>
<p><br /></p>
Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-43604444081500931712021-05-20T11:06:00.004-07:002021-05-20T11:15:13.535-07:00Fix Android Studio error: Missing essential plugin: org.jetbrains.androidJust update Android Studio 4.2.1, but fail to run with error of:
<div>
<br />
<div>
<b><span style="color: red;">Missing essential plugin: </span></b>
</div>
<div>
<b><span style="color: red;">org.jetbrains.android </span></b>
</div>
<div>
<span style="color: red;"><b>Please reinstall Android Studio from scratch.</b> </span>
</div>
<div><br /></div>
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEguMYyZLHt6t0h-k_LdE74js7LK1lBho657cO7yG1fVZDW6P2VUVWD5wNu2BdMst8e2r9xrtuy8uZHezDY6a0K-IIAXc0gX0BdhiGNFKKmaBhS2G_flI7ChTGWfYm_bejnO37-0qHoiq28/s653/Missing+essential+plugin.png" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="411" data-original-width="653" height="403" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEguMYyZLHt6t0h-k_LdE74js7LK1lBho657cO7yG1fVZDW6P2VUVWD5wNu2BdMst8e2r9xrtuy8uZHezDY6a0K-IIAXc0gX0BdhiGNFKKmaBhS2G_flI7ChTGWfYm_bejnO37-0qHoiq28/w640-h403/Missing+essential+plugin.png" width="640" /></a>
</div>
<br />
<div>Here how I fix it in my case, Android Studio 4.2.1 on Windows 10:</div><div><br /></div>
</div>
<center>
<iframe allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/bJ8OXyoAUJA" title="YouTube video player" width="560"></iframe>
</center>
<div>
<div><br /></div><div>
Search and delete
"C:\Users\user\AppData\Roaming\Google\AndroidStudio4.X\disabled_plugins.txt"
</div>
<div><br /></div>
<div>There are two in my setup:</div>
<div>
"C:\Users\user\AppData\Roaming\Google\AndroidStudio4.1\disabled_plugins.txt"
</div>
<div>
"C:\Users\user\AppData\Roaming\Google\AndroidStudio4.2\disabled_plugins.txt"
</div>
</div>
<div><br /></div>
<div>I delete both disabled_plugins.txt and re-start Android Studio.</div>
<div><br /></div>
Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-75900274445722175332021-01-04T12:09:00.003-08:002021-01-04T14:01:40.160-08:00Android read text file with request permission at runtime<p>Android example to read text file, with request permission at runtime.</p>
<center>
<iframe allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/DRsnrKtUuQc" width="560"></iframe>
</center>
<p>To read file in Android, if your app is installed on device that runs Android 6.0 (API level 23) or higher, you must request the dangerous permissions at runtime. (ref: <a href="https://developer.android.com/training/permissions/requesting" target="_blank">Android Developers : Request app permissions</a>)</p><p>Also shown in the video, access to /proc/net filesystem is restricted on Android 10+</p><p>On devices that run Android 10 or higher, apps cannot access /proc/net, which includes information about a device's network state. Apps that need access to this information, such as VPNs, should use the NetworkStatsManager or ConnectivityManager class. (ref: <a href="https://developer.android.com/about/versions/10/privacy/changes#proc-net-filesystem" target="_blank">Android Developers: Privacy changes in Android 10 > Restriction on access to /proc/net filesystem</a>)</p>
layout xml
<pre style="border: 1px solid black;"><code><span style="color: black;"><?xml version="1.0" encoding="utf-8"?>
<LinearLayout
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="horizontal"
tools:context=".MainActivity">
<LinearLayout
android:id="@+id/leftpanel"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:orientation="vertical"
android:background="@color/black"
android:layout_margin="5dp"
android:padding="5dp">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="20dp"
android:textStyle="bold"
android:textColor="@color/white"
android:text="android-er.blogspot.com"/>
<TextView
android:id="@+id/exercise"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="20dp"
android:textColor="@color/white"
android:text="Exercise: Read Text File"/>
<TextView
android:id="@+id/sysinfo"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="20dp"
android:textStyle="bold"
android:textColor="@color/white"/>
<TextView
android:id="@+id/sdkinfo"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="20dp"
android:textStyle="bold"
android:textColor="@color/white"/>
</LinearLayout>
<RelativeLayout
android:id="@+id/rightpanel"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:background="#C0C0C0"
android:layout_margin="5dp"
android:padding="5dp">
<Button
android:id="@+id/read"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="2dp"
android:text="Read"
android:layout_alignParentTop="true"/>
<TextView
android:id="@+id/filecontent"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_margin="2dp"
android:background="#808080"
android:fontFamily="monospace"
android:layout_below="@id/read"
android:layout_above="@id/msg"/>
<TextView
android:id="@+id/msg"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="2dp"
android:background="#404040"
android:layout_gravity="bottom"
android:layout_alignParentBottom="true"/>
</RelativeLayout>
</LinearLayout></span></code></pre>
Java code:
<pre style="border: 1px solid black;"><code><span style="color: black;">package android_er.blogspot.com.jexreadtextfile;
import android.Manifest;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.os.Build;
import android.os.Bundle;
import android.text.method.ScrollingMovementMethod;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
import androidx.core.app.ActivityCompat;
import androidx.core.content.ContextCompat;
import java.io.BufferedReader;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
public class MainActivity extends AppCompatActivity {
//Try different files
//String targetFile = "/sdcard/Download/Test.txt";
//String targetFile = "/proc/cpuinfo";
//String targetFile = "/proc/meminfo";
String targetFile = "/proc/net/arp"; //Restricted since Android 10
Button btnRead;
TextView tvFileContent;
TextView tvMsg;
final int PERMISSIONS_REQUEST_READ_EXTERNAL_STORAGE = 1;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
dispExInfo();
btnRead = findViewById(R.id.read);
btnRead.setText(targetFile);
tvFileContent = findViewById(R.id.filecontent);
//make this TextView scrollable
tvFileContent.setMovementMethod(new ScrollingMovementMethod());
tvMsg = findViewById(R.id.msg);
tvMsg.setText("Click on READ button");
btnRead.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
tvMsg.setText("READ button clicked");
toReadFile();
}
});
}
/*
Request Permission at Runtime, before read file.
*/
void toReadFile(){
if (ContextCompat.checkSelfPermission(this,
Manifest.permission.READ_EXTERNAL_STORAGE)
!= PackageManager.PERMISSION_GRANTED) {
// Permission is not granted
// Should we show an explanation?
if (ActivityCompat.shouldShowRequestPermissionRationale(
this,
Manifest.permission.READ_EXTERNAL_STORAGE)) {
// Show an explanation to the user *asynchronously* -- don't block
// this thread waiting for the user's response! After the user
// sees the explanation, try again to request the permission.
//to simplify, call requestPermissions again
Toast.makeText(getApplicationContext(),
"shouldShowRequestPermissionRationale",
Toast.LENGTH_LONG).show();
ActivityCompat.requestPermissions(this,
new String[]{Manifest.permission.READ_EXTERNAL_STORAGE},
PERMISSIONS_REQUEST_READ_EXTERNAL_STORAGE);
} else {
// No explanation needed; request the permission
ActivityCompat.requestPermissions(this,
new String[]{Manifest.permission.READ_EXTERNAL_STORAGE},
PERMISSIONS_REQUEST_READ_EXTERNAL_STORAGE);
}
}else{
// permission granted
readFile(targetFile);
}
}
@Override
public void onRequestPermissionsResult(
int requestCode,
@NonNull String[] permissions,
@NonNull int[] grantResults) {
if(requestCode == PERMISSIONS_REQUEST_READ_EXTERNAL_STORAGE){
if (grantResults.length > 0
&& grantResults[0] == PackageManager.PERMISSION_GRANTED) {
// permission was granted.
Toast.makeText(getApplicationContext(),
"permission was granted, thx:)",
Toast.LENGTH_LONG).show();
readFile(targetFile);
} else {
// permission denied.
Toast.makeText(getApplicationContext(),
"permission denied! Oh:(",
Toast.LENGTH_LONG).show();
}
return;
}else{
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
}
void readFile(String f){
File file = new File(f);
StringBuilder stringBuilder = new StringBuilder();
try {
BufferedReader bufferedReader = new BufferedReader(new FileReader(file));
String line;
while ((line = bufferedReader.readLine()) != null) {
stringBuilder.append(line);
stringBuilder.append('\n');
}
bufferedReader.close();
tvFileContent.setText(stringBuilder);
tvMsg.setText("Done");
} catch (FileNotFoundException e) {
e.printStackTrace();
tvMsg.setText(e.getMessage());
} catch (IOException e) {
e.printStackTrace();
tvMsg.setText(e.getMessage());
}
}
/* ==========================================
display Exercise info
*/
void dispExInfo(){
TextView tvExercise = findViewById(R.id.exercise);
TextView tvSysInfo = findViewById(R.id.sysinfo);
TextView tvSdkInfo = findViewById(R.id.sdkinfo);
tvExercise.append(" (Java)");
String manufacturer = Build.MANUFACTURER;
String model = Build.MODEL;
String release = Build.VERSION.RELEASE;
tvSysInfo.setText(
manufacturer + "\n"
+ model + "\n"
+ "Android: " + release + "\n");
PackageManager packageManager = getPackageManager();
String packageName = getPackageName();
int targetSdkVersion, minSdkVersion;
int versionCode;
String versionName;
try {
PackageInfo packageInfo =
packageManager.getPackageInfo(packageName, 0);
ApplicationInfo applicationInfo = packageInfo.applicationInfo;
targetSdkVersion = applicationInfo.targetSdkVersion;
minSdkVersion = applicationInfo.minSdkVersion;
tvSdkInfo.setText("targetSdkVersion = " + targetSdkVersion + "\n"
+ "minSdkVersion = " + minSdkVersion);
} catch (PackageManager.NameNotFoundException e) {
e.printStackTrace();
Toast.makeText(getApplicationContext(),
"NameNotFoundException: " + e.getMessage(),
Toast.LENGTH_LONG).show();
}
}
}
</span></code></pre>
<br />
uses-permission of "android.permission.READ_EXTERNAL_STORAGE" is needed in AndroidManifest.xml
<pre style="border: 1px solid black;"><code><span><?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="android_er.blogspot.com.jexreadtextfile">
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/Theme.JExReadTextFile">
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
<b><span style="color: red;"><uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/></span></b>
</manifest>
</span></code></pre>
<br />
<hr />
Kotlin version, basically auto-converted by Android Studio.
<pre style="border: 1px solid black;"><code><span style="color: black;">package android_er.blogspot.com.kexreadtextfile
import android.Manifest
import android.content.pm.PackageManager
import android.os.Build
import android.os.Bundle
import android.text.method.ScrollingMovementMethod
import android.view.View
import android.widget.Button
import android.widget.TextView
import android.widget.Toast
import androidx.appcompat.app.AppCompatActivity
import androidx.core.app.ActivityCompat
import androidx.core.content.ContextCompat
import java.io.*
class MainActivity : AppCompatActivity() {
//Try different files
//var targetFile = "/sdcard/Download/Test.txt";
var targetFile = "/proc/cpuinfo";
//var targetFile = "/proc/meminfo";
//var targetFile = "/proc/net/arp" //Restricted since Android 10
var btnRead: Button? = null
var tvFileContent: TextView? = null
var tvMsg: TextView? = null
val PERMISSIONS_REQUEST_READ_EXTERNAL_STORAGE = 1
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
dispExInfo()
btnRead = findViewById(R.id.read)
btnRead!!.setText(targetFile)
tvFileContent = findViewById(R.id.filecontent)
//make this TextView scrollable
tvFileContent!!.setMovementMethod(ScrollingMovementMethod())
tvMsg = findViewById(R.id.msg)
tvMsg!!.setText("Click on READ button")
btnRead!!.setOnClickListener(View.OnClickListener {
tvMsg!!.setText("READ button clicked")
toReadFile()
})
}
/*
Request Permission at Runtime, before read file.
*/
fun toReadFile() {
if (ContextCompat.checkSelfPermission(this,
Manifest.permission.READ_EXTERNAL_STORAGE)
!= PackageManager.PERMISSION_GRANTED) {
// Permission is not granted
// Should we show an explanation?
if (ActivityCompat.shouldShowRequestPermissionRationale(
this,
Manifest.permission.READ_EXTERNAL_STORAGE)) {
// Show an explanation to the user *asynchronously* -- don't block
// this thread waiting for the user's response! After the user
// sees the explanation, try again to request the permission.
//to simplify, call requestPermissions again
Toast.makeText(applicationContext,
"shouldShowRequestPermissionRationale",
Toast.LENGTH_LONG).show()
ActivityCompat.requestPermissions(this,
arrayOf(Manifest.permission.READ_EXTERNAL_STORAGE),
PERMISSIONS_REQUEST_READ_EXTERNAL_STORAGE)
} else {
// No explanation needed; request the permission
ActivityCompat.requestPermissions(this,
arrayOf(Manifest.permission.READ_EXTERNAL_STORAGE),
PERMISSIONS_REQUEST_READ_EXTERNAL_STORAGE)
}
} else {
// permission granted
readFile(targetFile)
}
}
override fun onRequestPermissionsResult(
requestCode: Int,
permissions: Array<String>,
grantResults: IntArray) {
if (requestCode == PERMISSIONS_REQUEST_READ_EXTERNAL_STORAGE) {
if (grantResults.size > 0
&& grantResults[0] == PackageManager.PERMISSION_GRANTED) {
// permission was granted.
Toast.makeText(applicationContext,
"permission was granted, thx:)",
Toast.LENGTH_LONG).show()
readFile(targetFile)
} else {
// permission denied.
Toast.makeText(applicationContext,
"permission denied! Oh:(",
Toast.LENGTH_LONG).show()
}
return
} else {
super.onRequestPermissionsResult(requestCode, permissions, grantResults)
}
}
fun readFile(f: String?) {
val file = File(f)
val stringBuilder = StringBuilder()
try {
val bufferedReader = BufferedReader(FileReader(file))
var line: String?
while (bufferedReader.readLine().also { line = it } != null) {
stringBuilder.append(line)
stringBuilder.append('\n')
}
bufferedReader.close()
tvFileContent!!.text = stringBuilder
tvMsg!!.text = "Done"
} catch (e: FileNotFoundException) {
e.printStackTrace()
tvMsg!!.text = e.message
} catch (e: IOException) {
e.printStackTrace()
tvMsg!!.text = e.message
}
}
/* ==========================================
display Exercise info
*/
fun dispExInfo() {
val tvExercise = findViewById<TextView>(R.id.exercise)
val tvSysInfo = findViewById<TextView>(R.id.sysinfo)
val tvSdkInfo = findViewById<TextView>(R.id.sdkinfo)
tvExercise.append(" (Kotlin)")
val manufacturer = Build.MANUFACTURER
val model = Build.MODEL
val release = Build.VERSION.RELEASE
tvSysInfo.text = """
$manufacturer
$model
Android: $release
""".trimIndent()
val packageManager = packageManager
val packageName = packageName
val targetSdkVersion: Int
val minSdkVersion: Int
var versionCode: Int
var versionName: String
try {
val packageInfo = packageManager.getPackageInfo(packageName, 0)
val applicationInfo = packageInfo.applicationInfo
targetSdkVersion = applicationInfo.targetSdkVersion
minSdkVersion = applicationInfo.minSdkVersion
tvSdkInfo.text = """
targetSdkVersion = $targetSdkVersion
minSdkVersion = $minSdkVersion
""".trimIndent()
} catch (e: PackageManager.NameNotFoundException) {
e.printStackTrace()
Toast.makeText(applicationContext,
"NameNotFoundException: " + e.message,
Toast.LENGTH_LONG).show()
}
}
}</span></code></pre><div class="separator" style="clear: both; text-align: center;"><a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjcxmXhOrryeEBkL_S42fo3fvMCkMBFj5i0JTOM_56joZzm1ZCjXYE5kk0kG82_bM9uWpLKSv0BBBk_0LHyeMkRiP-IIRjWKOjrrSHENy7R_BTsG1ZKzKpvLZGuRXMepA6KzW2HqRs2F74/s2000/kExReadTextFile.jpg" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="1200" data-original-width="2000" height="384" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjcxmXhOrryeEBkL_S42fo3fvMCkMBFj5i0JTOM_56joZzm1ZCjXYE5kk0kG82_bM9uWpLKSv0BBBk_0LHyeMkRiP-IIRjWKOjrrSHENy7R_BTsG1ZKzKpvLZGuRXMepA6KzW2HqRs2F74/w640-h384/kExReadTextFile.jpg" width="640" /></a></div><br />Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-29427080355138329592020-12-17T10:55:00.002-08:002020-12-17T10:58:36.645-08:00Android Kotlin exercise: detect touch on individual view<p> This example show how to detect touch on individual view.</p>
<center>
<iframe allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/tZB2iKwL2NI" width="560"></iframe>
</center>
<br />
Example code
<pre style="border: 1px solid black;"><code><span style="color: black;">
package com.blogspot.android_er.exmyview
import android.os.Build
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.view.MotionEvent
import android.widget.ImageView
import android.widget.TextView
/*
ref:
https://developer.android.com/training/gestures/detector#capture-touch-events-for-a-single-view
Android Developers Guides > Detect common gestures > Capture touch events for a single view
*/
class MainActivity : AppCompatActivity() {
private lateinit var ivIcon: ImageView
private lateinit var tvSysInfo: TextView
private lateinit var tvSdkInfo: TextView
private lateinit var tvConsole: TextView
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
ivIcon = findViewById(R.id.icon)
tvSysInfo = findViewById(R.id.sysinfo)
tvSdkInfo = findViewById(R.id.sdkinfo)
tvConsole = findViewById(R.id.console)
val manufacturer = Build.MANUFACTURER
val model = Build.MODEL
val release = Build.VERSION.RELEASE
val pkgInfo = packageManager.getPackageInfo(packageName, 0)
val appInfo = pkgInfo.applicationInfo
val targetSdkVersion = appInfo.targetSdkVersion
val minSdkVersion = appInfo.minSdkVersion
tvSysInfo.text = manufacturer + "\n" +
model + "\n" + "Android: " + release
tvSdkInfo.text = "targetSdkVersion: " + targetSdkVersion + "\n" +
"minSdkVersion: " + minSdkVersion
tvConsole.text = "Android Example:" +
"\nCapture touch events for a single view"
ivIcon.setOnTouchListener { v, event -> // ... Respond to touch events
/*
return true if the listener has consumed the event, false otherwise.
*/
val action = event.action
when (action) {
MotionEvent.ACTION_DOWN -> {
/*
Beware of creating a listener that returns false
for the ACTION_DOWN event.
If you do this, the listener will not be called
for the subsequent ACTION_MOVE and ACTION_UP string of events.
This is because ACTION_DOWN is the starting point for all touch events.
*/
tvConsole.text = "ACTION_DOWN@ivIcon"
true}
MotionEvent.ACTION_MOVE -> {
tvConsole.append("\nACTION_MOVE@ivIcon")
true}
MotionEvent.ACTION_UP -> {
tvConsole.text = "ACTION_UP@ivIcon"
true}
MotionEvent.ACTION_CANCEL -> {
tvConsole.text = "ACTION_CANCEL@ivIcon"
true}
MotionEvent.ACTION_OUTSIDE -> {
tvConsole.text = "ACTION_OUTSIDE@ivIcon"
true}
else -> super.onTouchEvent(event)
}
}
tvSysInfo.setOnTouchListener { v, event -> // ... Respond to touch events
when (event.action) {
MotionEvent.ACTION_DOWN -> {
tvConsole.text = "ACTION_DOWN@tvSysInfo"
true}
MotionEvent.ACTION_MOVE -> {
tvConsole.append("\nACTION_MOVE@tvSysInfo")
true}
MotionEvent.ACTION_UP -> {
tvConsole.text = "ACTION_UP@tvSysInfo"
true}
MotionEvent.ACTION_CANCEL -> {
tvConsole.text = "ACTION_CANCEL@tvSysInfo"
true}
MotionEvent.ACTION_OUTSIDE -> {
tvConsole.text = "ACTION_OUTSIDE@tvSysInfo"
true}
else -> super.onTouchEvent(event)
}
}
tvSdkInfo.setOnTouchListener { v, event -> // ... Respond to touch events
when (event.action) {
MotionEvent.ACTION_DOWN -> {
tvConsole.text = "ACTION_DOWN@tvSdkInfo"
true}
MotionEvent.ACTION_MOVE -> {
tvConsole.append("\nACTION_MOVE@tvSdkInfo")
true}
MotionEvent.ACTION_UP -> {
tvConsole.text = "ACTION_UP@tvSdkInfo"
true}
MotionEvent.ACTION_CANCEL -> {
tvConsole.text = "ACTION_CANCEL@tvSdkInfo"
true}
MotionEvent.ACTION_OUTSIDE -> {
tvConsole.text = "ACTION_OUTSIDE@tvSdkInfo"
true}
else -> super.onTouchEvent(event)
}
}
}
}
</span></code></pre>
<br />
layout
<pre style="border: 1px solid black;"><code><span style="color: black;"><?xml version="1.0" encoding="utf-8"?>
<LinearLayout
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="horizontal"
tools:context=".MainActivity">
<LinearLayout
android:id="@+id/leftpanel"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1"
android:orientation="vertical"
android:background="#E0E0E0"
android:layout_margin="5dp">
<ImageView
android:id="@+id/icon"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="5dp"
android:padding="5dp"
android:background="#0000F0"
android:src="@mipmap/ic_launcher_round"/>
<TextView
android:id="@+id/sysinfo"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="5dp"
android:padding="5dp"
android:background="#0000D0"
android:textSize="20dp"
android:textStyle="bold"
android:textColor="@color/white"/>
<TextView
android:id="@+id/sdkinfo"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="5dp"
android:padding="5dp"
android:background="#0000B0"
android:textSize="20dp"
android:textStyle="bold"
android:textColor="@color/white"/>
</LinearLayout>
<LinearLayout
android:id="@+id/rightpanel"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1"
android:orientation="vertical"
android:background="#C0C0C0">
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="5dp"
android:padding="5dp"
android:textSize="20dp"
android:textStyle="bold"
android:textColor="@color/white"
android:text="android-er.blogspot.com"/>
<TextView
android:id="@+id/console"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="5dp"
android:padding="5dp"
android:textSize="30dp"
android:textStyle="bold"
android:gravity="bottom"/>
</LinearLayout>
</LinearLayout>
</span></code></pre>Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-86926218509533088912020-12-11T11:27:00.004-08:002020-12-11T11:27:33.517-08:00Linux Mint: Add Program Launcher to Menu<p>As a example, this video show how to Add Program Launcher to Menu on Linux Mint 20, to run idea.sh in /opt/idea-IC-203.5981.155/bin folder.</p>
<center>
<iframe allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/0CFNCkMKp44" width="560"></iframe>
<center></center></center>Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-38549469573854263682020-12-10T15:06:00.005-08:002020-12-11T11:29:16.450-08:00Install IntelliJ IDEA on Linux Mint 20Steps to install Jetbrains IntelliJ IDEA Community Edition 2020.3 on Linux Mint 20, tested on VirtualBox.<div>
<center>
<iframe allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/0e1SVL7j0_8" width="560"></iframe></center>
<p>IntelliJ IDEA is a cross-platform IDE on the Windows, macOS, and Linux operating systems. It is available in the following editions:</p><ul style="text-align: left;"><li>Community Edition is free and open-source, licensed under Apache 2.0. It provides all the basic features for JVM and Android development.</li><li>IntelliJ IDEA Ultimate is commercial, distributed with a 30-day trial period. It provides additional tools and features for web and enterprise development.</li></ul><p></p><p><b>To install IntelliJ IDEA Community Edition on Linux Mint:</b></p><p>Visit: <a href="https://www.jetbrains.com/idea/download/" target="_blank">https://www.jetbrains.com/idea/download/</a></p><p>Download .tar.gz of Community Edition.</p><p>Extract the tarball to a directory that supports file execution.<br />For example, to extract it to the recommended /opt directory, run the following command:</p><p>$ sudo tar -xzf <downloaded file> -C /opt</p><p>Execute the idea.sh script from the extracted directory to run IntelliJ IDEA. or <a href="https://android-er.blogspot.com/2020/12/linux-mint-add-program-launcher-to-menu.html"><b>add a program launcher to Linux Mint Menu to run idea.sh</b></a>.</p><p>ref: <a href="https://www.jetbrains.com/help/idea/installation-guide.html" target="_blank">https://www.jetbrains.com/help/idea/installation-guide.html</a></p><p><br /></p></div>Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-78152246359782054222020-11-14T06:59:00.002-08:002020-11-14T06:59:58.742-08:00How to power-on without using POWER button, Xiaomi/Redmi PhoneIt is a common case that the POWER button of your phone is broken, such that you cannot power it on in power-off mode. This video show how to power up Xiaomi phone in Recovery Mode, then switch to normal mode, without POWER button.<div>
<center>
<iframe allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/gfX93p7_jFg" width="560"></iframe></center>
<br />
<p><b>How to power-on without using POWER button, Xiaomi/Redmi Phone</b></p><p>When phone is Power OFF:<br />Press and Hold VOL-UP button, Insert USB Power cable, to enter Recovery Mode.</p><p>With Reboot option selected, just WAIT, the phone will reboot in around 4 minutes.</p><p>Tested on Xiaomi Mi 10 Lite 5G, also Redmi 5 Plus/Note 4X.</p><p><br /></p></div>Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-80525366792078813502020-11-02T13:02:00.004-08:002020-11-03T12:25:15.321-08:00Android exercise: ImageFilterView (Kotlin)<p><b><a href="https://developer.android.com/reference/androidx/constraintlayout/utils/widget/ImageFilterView" target="_blank">ImageFilterView</a></b> is a An ImageView that can display, combine and filter images, to handle various common filtering operations. You can set saturation, contrast, warmth and some othters (refer to the document) in layout XML, or change it at run-time.</p><p>
</p><center>
<iframe allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/HQIOdMTPuOY" width="560"></iframe>
</center>
<p></p><p>ImageFilterView was added in ConstraintLayout 2.0, so make sure dependencies of implementation 'androidx.constraintlayout:constraintlayout:2.0.0' or higher is include in your build.grade(Module:) file.</p><div class="separator" style="clear: both; text-align: center;"><a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEj4vJ2-dRhbvq1Nyf1iEPHTpHi8RIGhqpEa4Bp3sSDqvzTlB2LaJcNHO9dsIzf9SWWCbxRKPINnc-Ugo9wgra5jBnQV00GT-EEu95dBEVwSKKiU7t-NLUn4Ne_GFJcetP6Ekxtvdxh_pnk/s1366/ConstraintLayout+dependencies.png" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="768" data-original-width="1366" height="360" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEj4vJ2-dRhbvq1Nyf1iEPHTpHi8RIGhqpEa4Bp3sSDqvzTlB2LaJcNHO9dsIzf9SWWCbxRKPINnc-Ugo9wgra5jBnQV00GT-EEu95dBEVwSKKiU7t-NLUn4Ne_GFJcetP6Ekxtvdxh_pnk/w640-h360/ConstraintLayout+dependencies.png" width="640" /></a></div><div><br /></div>build.grade(Module:)<br />
<pre style="border: 1px solid black;"><code><span style="color: black;">dependencies {
implementation 'androidx.constraintlayout:constraintlayout:2.0.4'
}
</span></code></pre>
Layout XML:
<pre style="border: 1px solid black;"><code><span><?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.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:layout_margin="20dp"
tools:context=".MainActivity">
<LinearLayout
android:id="@+id/header"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
app:layout_constraintBottom_toTopOf="@id/imagefilterview"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="ImageFilterView Example (Kotlin)"
android:textStyle="bold" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Android-er.blogspot.com" />
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="@android:mipmap/sym_def_app_icon"/>
</LinearLayout>
<b><span style="color: red;"><androidx.constraintlayout.utils.widget.ImageFilterView
android:id="@+id/imagefilterview"
android:src="@android:mipmap/sym_def_app_icon"
android:layout_width="0dp"
android:layout_height="0dp"
app:layout_constraintBottom_toTopOf="@id/panel"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toBottomOf="@id/header"
app:saturation="1.0"
app:contrast="1.0"
app:brightness="1.0"/></span></b>
<LinearLayout
android:id="@+id/panel"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toBottomOf="@id/imagefilterview">
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Saturation"/>
<TextView
android:id="@+id/sat"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
<SeekBar
android:id="@+id/seekBarSat"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="100"
android:progress="50"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Contrast"/>
<TextView
android:id="@+id/cont"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
<SeekBar
android:id="@+id/seekBarCont"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="100"
android:progress="50"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Warmth"/>
<TextView
android:id="@+id/warm"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
<SeekBar
android:id="@+id/seekBarWarm"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="100"
android:progress="50"/>
</LinearLayout>
</androidx.constraintlayout.widget.ConstraintLayout>
</span></code></pre><div>Kotlin code:
<pre style="border: 1px solid black;"><code><span style="color: black;">package com.blogspot.android_er.eximgfilterview2
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.widget.SeekBar
import android.widget.TextView
import androidx.constraintlayout.utils.widget.ImageFilterView
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val MyImageFilterView =
findViewById<ImageFilterView>(R.id.imagefilterview)
val MySeekBarSat = findViewById<SeekBar>(R.id.seekBarSat)
val MyTextViewSat = findViewById<TextView>(R.id.sat)
val MySeekBarCont = findViewById<SeekBar>(R.id.seekBarCont)
val MyTextViewCont = findViewById<TextView>(R.id.cont)
val MySeekBarWarm = findViewById<SeekBar>(R.id.seekBarWarm)
val MyTextViewWarm = findViewById<TextView>(R.id.warm)
//Get the first-run setting of saturation, contrast and warmth
MyTextViewSat.text= MyImageFilterView.saturation.toString()
MyTextViewCont.text= MyImageFilterView.contrast.toString()
MyTextViewWarm.text= MyImageFilterView.warmth.toString()
MySeekBarSat.setOnSeekBarChangeListener(
object : SeekBar.OnSeekBarChangeListener{
override fun onProgressChanged(seekBar: SeekBar?,
progress: Int, fromUser: Boolean) {
//update saturation
MyImageFilterView.saturation = (progress / 100.0f) * 2
//read back the saturation
MyTextViewSat.text= MyImageFilterView.saturation.toString()
}
override fun onStartTrackingTouch(seekBar: SeekBar?) {}
override fun onStopTrackingTouch(seekBar: SeekBar?) {}
})
MySeekBarCont.setOnSeekBarChangeListener(
object : SeekBar.OnSeekBarChangeListener{
override fun onProgressChanged(seekBar: SeekBar?,
progress: Int, fromUser: Boolean) {
MyImageFilterView.contrast = (progress / 100.0f) * 2
MyTextViewCont.text= MyImageFilterView.contrast.toString()
}
override fun onStartTrackingTouch(seekBar: SeekBar?) {}
override fun onStopTrackingTouch(seekBar: SeekBar?) {}
})
MySeekBarWarm.setOnSeekBarChangeListener(
object : SeekBar.OnSeekBarChangeListener{
override fun onProgressChanged(seekBar: SeekBar?,
progress: Int, fromUser: Boolean) {
MyImageFilterView.warmth = (progress / 100.0f) * 2
MyTextViewWarm.text= MyImageFilterView.warmth.toString()
}
override fun onStartTrackingTouch(seekBar: SeekBar?) {}
override fun onStopTrackingTouch(seekBar: SeekBar?) {}
})
}
}
</span></code></pre>
</div><div><p><br /></p></div><hr />
Then add the feature to change Crossfade, also show how overlay setting affect the crossfade result.<div><br /></div><div>
<center>
<iframe allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/5ggjjWsn-BA" width="560"></iframe>
</center>
</div><div><br /></div><div>Layout XML:</div><div><br />
<pre style="border: 1px solid black;"><code><span><?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.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:layout_margin="20dp"
tools:context=".MainActivity">
<LinearLayout
android:id="@+id/header"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
app:layout_constraintBottom_toTopOf="@id/imagefilterview"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="ImageFilterView Example (Kotlin)"
android:textStyle="bold" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Android-er.blogspot.com" />
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="@android:mipmap/sym_def_app_icon"/>
</LinearLayout>
<b><span style="color: red;"><androidx.constraintlayout.utils.widget.ImageFilterView
android:id="@+id/imagefilterview"
android:layout_width="0dp"
android:layout_height="0dp"
app:layout_constraintBottom_toTopOf="@id/panel"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toBottomOf="@id/header"
android:src="@android:mipmap/sym_def_app_icon"
app:altSrc="@android:drawable/btn_star_big_on"
app:overlay="false"
app:crossfade="0.0"
app:saturation="1.0"
app:contrast="1.0"
app:warmth="1.0"
/>
</span></b>
<LinearLayout
android:id="@+id/panel"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toBottomOf="@id/imagefilterview">
<b><span style="color: red;"><TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Crossfade"/>
<TextView
android:id="@+id/crossfade"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
<SeekBar
android:id="@+id/seekBarCrossfade"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="100"
android:progress="0"/></span></b>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Saturation"/>
<TextView
android:id="@+id/sat"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
<SeekBar
android:id="@+id/seekBarSat"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="100"
android:progress="50"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Contrast"/>
<TextView
android:id="@+id/cont"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
<SeekBar
android:id="@+id/seekBarCont"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="100"
android:progress="50"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Warmth"/>
<TextView
android:id="@+id/warm"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
<SeekBar
android:id="@+id/seekBarWarm"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:max="100"
android:progress="50"/>
</LinearLayout>
</androidx.constraintlayout.widget.ConstraintLayout>
</span></code></pre></div><div><br /></div><div>Kotlin code:</div><div><br />
<pre style="border: 1px solid black;"><code><span>package com.blogspot.android_er.eximgfilterview2
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.widget.SeekBar
import android.widget.TextView
import androidx.constraintlayout.utils.widget.ImageFilterView
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val MyImageFilterView =
findViewById<ImageFilterView>(R.id.imagefilterview)
<b><span style="color: red;">val MySeekBarCrossfade = findViewById<SeekBar>(R.id.seekBarCrossfade)
val MyTextViewCrossfade = findViewById<TextView>(R.id.crossfade)</span></b>
val MySeekBarSat = findViewById<SeekBar>(R.id.seekBarSat)
val MyTextViewSat = findViewById<TextView>(R.id.sat)
val MySeekBarCont = findViewById<SeekBar>(R.id.seekBarCont)
val MyTextViewCont = findViewById<TextView>(R.id.cont)
val MySeekBarWarm = findViewById<SeekBar>(R.id.seekBarWarm)
val MyTextViewWarm = findViewById<TextView>(R.id.warm)
//Get the first-run setting of crossfade, saturation, contrast and warmth
<b><span style="color: red;">MyTextViewCrossfade.text= MyImageFilterView.crossfade.toString()</span></b>
MyTextViewSat.text= MyImageFilterView.saturation.toString()
MyTextViewCont.text= MyImageFilterView.contrast.toString()
MyTextViewWarm.text= MyImageFilterView.warmth.toString()
<b><span style="color: red;">MySeekBarCrossfade.setOnSeekBarChangeListener(
object : SeekBar.OnSeekBarChangeListener{
override fun onProgressChanged(seekBar: SeekBar?,
progress: Int, fromUser: Boolean) {
//update saturation
MyImageFilterView.crossfade = (progress / 100.0f)
//read back the saturation
MyTextViewCrossfade.text= MyImageFilterView.crossfade.toString()
}
override fun onStartTrackingTouch(seekBar: SeekBar?) {}
override fun onStopTrackingTouch(seekBar: SeekBar?) {}
})</span></b>
MySeekBarSat.setOnSeekBarChangeListener(
object : SeekBar.OnSeekBarChangeListener{
override fun onProgressChanged(seekBar: SeekBar?,
progress: Int, fromUser: Boolean) {
//update saturation
MyImageFilterView.saturation = (progress / 100.0f) * 2
//read back the saturation
MyTextViewSat.text= MyImageFilterView.saturation.toString()
}
override fun onStartTrackingTouch(seekBar: SeekBar?) {}
override fun onStopTrackingTouch(seekBar: SeekBar?) {}
})
MySeekBarCont.setOnSeekBarChangeListener(
object : SeekBar.OnSeekBarChangeListener{
override fun onProgressChanged(seekBar: SeekBar?,
progress: Int, fromUser: Boolean) {
MyImageFilterView.contrast = (progress / 100.0f) * 2
MyTextViewCont.text= MyImageFilterView.contrast.toString()
}
override fun onStartTrackingTouch(seekBar: SeekBar?) {}
override fun onStopTrackingTouch(seekBar: SeekBar?) {}
})
MySeekBarWarm.setOnSeekBarChangeListener(
object : SeekBar.OnSeekBarChangeListener{
override fun onProgressChanged(seekBar: SeekBar?,
progress: Int, fromUser: Boolean) {
MyImageFilterView.warmth = (progress / 100.0f) * 2
MyTextViewWarm.text= MyImageFilterView.warmth.toString()
}
override fun onStartTrackingTouch(seekBar: SeekBar?) {}
override fun onStopTrackingTouch(seekBar: SeekBar?) {}
})
}
}
</span></code></pre></div>
<br />Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-46487005655291134112020-10-11T14:08:00.001-07:002020-10-11T14:08:47.169-07:00What's the difference between system image with Google API and Google APIs? when create Android Virtual Device<p> </p><div class="separator" style="clear: both; text-align: center;"><a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjrB0UQ5_BF88j-WtlYRYoTWACesq-DSpfsuZcAg6Lr98jA7lEFfO5Xk6L9ip2ZyyIyKRj45zAxsUonyPq8_bdWWk6rmu4c_rYx0COmQ89SzfxTljvkNLQJ-r_b2MpD1DCY30dv7CEXmBY/s1366/Select+a+system+image.png" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="768" data-original-width="1366" height="360" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjrB0UQ5_BF88j-WtlYRYoTWACesq-DSpfsuZcAg6Lr98jA7lEFfO5Xk6L9ip2ZyyIyKRj45zAxsUonyPq8_bdWWk6rmu4c_rYx0COmQ89SzfxTljvkNLQJ-r_b2MpD1DCY30dv7CEXmBY/w640-h360/Select+a+system+image.png" width="640" /></a></div><br /><p></p><p>When you create a Android Virtual Device, you have to select a system image from a list of available images. Some marked Google Play, and some marked Google APIs, so what's the difference?</p><p><i><b>A system image labeled with Google APIs includes access to Google Play services. A system image labeled with the Google Play logo in the Play Store column includes the Google Play Store app and access to Google Play services.</b></i></p><p>reference: <a href="https://developer.android.com/studio/run/managing-avds#system-image" target="_blank">https://developer.android.com/studio/run/managing-avds#system-image</a></p><div class="separator" style="clear: both; text-align: center;"><a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjfEWSsz7uWnsZTAF1pSqahLQM32tugUBPlTpu_QV1W4eA1RQ4QBa-8fU18ABCmqBO4N7JNQk4Z9LySymP2OmFdtiMgWdnoMiWTk0nxHgKaQJ86gAPfiwI-NCdjU5Vb-tS0qgAQlWNsohs/s1366/System+Images.png" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="768" data-original-width="1366" height="360" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjfEWSsz7uWnsZTAF1pSqahLQM32tugUBPlTpu_QV1W4eA1RQ4QBa-8fU18ABCmqBO4N7JNQk4Z9LySymP2OmFdtiMgWdnoMiWTk0nxHgKaQJ86gAPfiwI-NCdjU5Vb-tS0qgAQlWNsohs/w640-h360/System+Images.png" width="640" /></a></div><br /><p><i>Including a Google Play tab in the Extended controls dialog that provides a convenient button for updating Google Play services on the device.</i></p><div class="separator" style="clear: both; text-align: center;"><a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEg3dQNCYEldUE1Fd3Jjn30e-wyiJsyX0ZGL9bpLB1THzQYgEWPAO310npowMEPIgrh5Xxbw9NLiexb5_3r-nZ0MZhbYlFpt3FSaYRosoxD-cCfm6B1wLXPgi3WjivpIJ4rartMC65bRfOw/s1366/Google+Play+Services.png" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="768" data-original-width="1366" height="360" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEg3dQNCYEldUE1Fd3Jjn30e-wyiJsyX0ZGL9bpLB1THzQYgEWPAO310npowMEPIgrh5Xxbw9NLiexb5_3r-nZ0MZhbYlFpt3FSaYRosoxD-cCfm6B1wLXPgi3WjivpIJ4rartMC65bRfOw/w640-h360/Google+Play+Services.png" width="640" /></a></div><br /><p><br /></p><p><br /></p><p><br /></p>Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-40379925884714101152020-09-03T06:57:00.002-07:002020-09-03T06:59:53.440-07:00Kotlin Multiplatform Mobile Alpha and portal released<p>Kotlin Multiplatform Mobile is a solution to write once for Android and iOS apps, using Kotlin.</p><p>Kotlin Multiplatform Mobile is an SDK that allows developers to use the same business logic code in both iOS and Android applications. KMM now goes Alpha, and you can start sharing business logic in your mobile apps with it right away. It includes the new KMM Plugin for Android Studio, which allows you to write, run, test, and debug shared code in the same IDE.</p><p>details: <a href="https://blog.jetbrains.com/kotlin/2020/08/kotlin-multiplatform-mobile-goes-alpha/" target="_blank">Kotlin Blog - Kotlin Multiplatform Mobile Goes Alpha</a></p><p>The new <a href="https://kotlinlang.org/lp/mobile/" target="_blank">Kotlin Multiplatform Mobile developer portal</a> is up, have all you need to know to create cross-platform apps.</p><p><br /></p>Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-79735333189552554422020-08-26T10:44:00.005-07:002020-08-26T10:44:52.614-07:00Chronometer example (Kotlin)<p> <span color="" face="" style="white-space: pre-wrap;">Android example of using Chronometer (count-up and count-down) widget, with Kotlin</span></p><center><span color="" face="" style="white-space: pre-wrap;"><iframe allow="accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/INZ0Mg-mYwY" width="560"></iframe>
</span></center><span color="" face="" style="white-space: pre-wrap;">
</span><p></p><p><span color="" face="" style="white-space: pre-wrap;">Layout with Chronometer</span></p>
<pre style="border: 1px solid black;"><code><span style="color: black;"><?xml version="1.0" encoding="utf-8"?>
<LinearLayout
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"
tools:context=".MainActivity"
android:layout_margin="10dp">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textStyle="bold"
android:text="Chronometer Example (Kotlin)"
android:layout_gravity="center"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Android-er.blogspot.com"
android:layout_gravity="center"/>
<Chronometer
android:id="@+id/chronometer"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textSize="34dp"
android:textStyle="bold"/>
<Button
android:id="@+id/start"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Start (Count Up)"/>
<Button
android:id="@+id/stop"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Stop"/>
<Button
android:id="@+id/reset"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Reset"/>
<Chronometer
android:id="@+id/chronometerDn"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textSize="34dp"
android:textStyle="bold"
android:countDown="true"/>
<Button
android:id="@+id/startDn"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Start (Count Down)"/>
<Button
android:id="@+id/stopDn"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Stop"/>
<Button
android:id="@+id/resetDn"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Reset"/>
</LinearLayout>
</span></code></pre>
Android Kotlin code<div><br />
<br /></div>
<pre style="border: 1px solid black;"><code><span style="color: black;">package com.blogspot.android_er.androidchronometer
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.os.SystemClock
import android.widget.Button
import android.widget.Chronometer
import android.widget.Toast
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val myChronometer = findViewById<Chronometer>(R.id.chronometer)
val btnStart = findViewById<Button>(R.id.start)
val btnStop = findViewById<Button>(R.id.stop)
val btnReset = findViewById<Button>(R.id.reset)
btnStart.setOnClickListener(){
myChronometer.start();
Toast.makeText(this,
"myChronometer.start()",
Toast.LENGTH_LONG).show()
}
btnStop.setOnClickListener(){
myChronometer.stop();
Toast.makeText(this,
"myChronometer.stop()",
Toast.LENGTH_LONG).show()
}
btnReset.setOnClickListener(){
myChronometer.base = SystemClock.elapsedRealtime()
Toast.makeText(this,
"myChronometer.base = SystemClock.elapsedRealtime()",
Toast.LENGTH_LONG).show()
}
val myChronometerDn = findViewById<Chronometer>(R.id.chronometerDn)
val btnStartDn = findViewById<Button>(R.id.startDn)
val btnStopDn = findViewById<Button>(R.id.stopDn)
val btnResetDn = findViewById<Button>(R.id.resetDn)
btnStartDn.setOnClickListener(){
myChronometerDn.base = SystemClock.elapsedRealtime() + 10000
myChronometerDn.start()
Toast.makeText(this,
"myChronometerDn.base = " +
"SystemClock.elapsedRealtime() + 10000 \n" +
"myChronometerDn.start()",
Toast.LENGTH_LONG).show()
}
btnStopDn.setOnClickListener(){
myChronometerDn.stop()
Toast.makeText(this,
"myChronometerDn.stop()",
Toast.LENGTH_LONG).show()
}
btnResetDn.setOnClickListener(){
myChronometerDn.base = SystemClock.elapsedRealtime()
Toast.makeText(this,
"myChronometerDn.base = SystemClock.elapsedRealtime()",
Toast.LENGTH_LONG).show()
}
}
}
</span></code></pre>
<br />
<br />Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-25701388239578377802020-08-22T11:12:00.004-07:002020-08-22T11:12:52.222-07:00Simple example using TextClock with Kotlin<p><a href="https://developer.android.com/reference/android/widget/TextClock" target="_blank">TextClock</a> can display the current date and/or time as a formatted string. It's a simple example of using TextClock with Kotlin.</p><div class="separator" style="clear: both; text-align: center;"><a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjvzYG_Yw38Kn_245JHo9kVlMVVraDaGn0X8ZA_Khdmc8Rafd5NvVHZ-K-yvWEfNmU1kR2lqM3Q9ZPy9Vefjx9PGZGq0y6Bp5JpGOZTd-4hUlX6BifrX9JXBRWs-n_UQJ3pGaQJqwuvahc/s1920/TextClock.png" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="1920" data-original-width="1080" height="640" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjvzYG_Yw38Kn_245JHo9kVlMVVraDaGn0X8ZA_Khdmc8Rafd5NvVHZ-K-yvWEfNmU1kR2lqM3Q9ZPy9Vefjx9PGZGq0y6Bp5JpGOZTd-4hUlX6BifrX9JXBRWs-n_UQJ3pGaQJqwuvahc/s640/TextClock.png" /></a></div><p>layout XML with TextClock</p>
<pre style="border: 1px solid black;"><code><span style="color: black;"><?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.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"
tools:context=".MainActivity">
<TextClock
android:id="@+id/mytextclock"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textStyle="italic|bold"
android:textSize="40dp"
android:format12Hour="hh:mm:ss a"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent"
/>
</androidx.constraintlayout.widget.ConstraintLayout>
</span></code></pre>
<p>Access TextClock using Kotlin</p>
<pre style="border: 1px solid black;"><code><span style="color: black;">package com.blogspot.android_er.androidtextclock
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.view.View
import android.widget.TextClock
import android.widget.Toast
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val myTextClock = findViewById<TextClock>(R.id.mytextclock)
myTextClock.setOnClickListener{
val s = myTextClock.text
Toast.makeText(this, s, Toast.LENGTH_LONG).show()
}
}
}
</span></code></pre><br />
<br />Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-15214661118251047782020-08-21T13:44:00.001-07:002020-08-21T13:44:03.798-07:00Get Android and SDK version using Kotlin<p> Exercise to get Android device info and compile SDK version using Kotlin.</p><table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto;"><tbody><tr><td style="text-align: center;"><a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEizDs3iV2aYC96G1sXquw5HEFbgJeaGO0XyiYYiuNI-6YZpnBurqBhHN31QnVIg-80TQVQcKJlv_QcLIKMmFLketYmTU8BUPp1TRtKbqb7m3Ejg9LIeXeExSwddEeJlOKWogXDKIG3xmGc/s1366/AndroidInfo.png" style="margin-left: auto; margin-right: auto;"><img border="0" data-original-height="768" data-original-width="1366" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEizDs3iV2aYC96G1sXquw5HEFbgJeaGO0XyiYYiuNI-6YZpnBurqBhHN31QnVIg-80TQVQcKJlv_QcLIKMmFLketYmTU8BUPp1TRtKbqb7m3Ejg9LIeXeExSwddEeJlOKWogXDKIG3xmGc/s640/AndroidInfo.png" width="640" /></a></td></tr><tr><td class="tr-caption" style="text-align: center;">Run on Android Emulator of Android 10<br /></td></tr></tbody></table><div class="separator" style="clear: both; text-align: center;"><br /></div><table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto;"><tbody><tr><td style="text-align: center;"><a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEg0SN9x72ix8A3n417A3mQJ0qVX9XfOaB_GWJ_GVrwO92Cr2Az6deoG4WVOQLiJM2c7aYOSxSzG1ls1ImcbSuVsQMqnDIaPJSpJpVw9dFbNAAFjIHpCTlOCqqGbBnuIDFokXpNuW3Iczt8/s2160/com.blogspot.android_er.androidinfo.jpg" style="margin-left: auto; margin-right: auto;"><img border="0" data-original-height="2160" data-original-width="1080" height="640" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEg0SN9x72ix8A3n417A3mQJ0qVX9XfOaB_GWJ_GVrwO92Cr2Az6deoG4WVOQLiJM2c7aYOSxSzG1ls1ImcbSuVsQMqnDIaPJSpJpVw9dFbNAAFjIHpCTlOCqqGbBnuIDFokXpNuW3Iczt8/s640/com.blogspot.android_er.androidinfo.jpg" /></a></td></tr><tr><td class="tr-caption" style="text-align: center;">Run on Redmi 5 Plus (Android 8.1.0)<br /></td></tr></tbody></table><p>MainActivity.kt</p>
<pre style="border: 1px solid black;"><code><span style="color: black;">package com.blogspot.android_er.androidinfo
import android.os.Build
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.widget.TextView
import androidx.annotation.RequiresApi
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val manufacturer = Build.MANUFACTURER
val model = Build.MODEL
val release = Build.VERSION.RELEASE
val pkgInfo = packageManager.getPackageInfo(packageName, 0)
val appInfo = pkgInfo.applicationInfo
val targetSdkVersion = appInfo.targetSdkVersion
val minSdkVersion = appInfo.minSdkVersion
//Display system and SDK info for reference
val tvInfo = findViewById<TextView>(R.id.info)
tvInfo.setText(manufacturer + "\n" +
model + "\n" +
"Android: " + release + "\n" +
"targetSdkVersion: " + targetSdkVersion + "\n" +
"minSdkVersion: " + minSdkVersion)
}
}
</span></code></pre>
<p>layout xml</p>
<pre style="border: 1px solid black;"><code><span style="color: black;"><?xml version="1.0" encoding="utf-8"?>
<LinearLayout
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"
tools:context=".MainActivity">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Android-er"
android:textStyle="bold"
android:textSize="34dp" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="android-er.blogspot.com " />
<TextView
android:id="@+id/info"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textStyle="italic"
android:textSize="30dp"/>
</LinearLayout>
</span></code></pre><br />
<br />Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-55005161124976220522020-07-22T17:47:00.001-07:002020-07-22T17:48:13.166-07:00Android Codelab - Getting Started with CameraX<p>The Android developer codelab, Getting Started with CameraX, guide you how to create a camera app that uses CameraX to show a viewfinder, take photos, and analyze an image stream from the camera.</p><p>Introduce the concept of <em>use cases</em> in CameraX, which you can use for a variety of camera operations, from displaying a viewfinder to analyzing frames in real time.</p><p><a href="https://codelabs.developers.google.com/codelabs/camerax-getting-started/">Android developer codelab, Getting Started with CameraX</a><br></p><p><br></p><p><br></p>Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-86052127146469926842020-07-17T14:15:00.002-07:002020-07-17T14:15:49.188-07:00Support for newer Java language APIs<center>
<iframe allow="accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/heCvGfOGH0s" width="560"></iframe>
</center>
<br />
When you use Android Gradle Plugin 4.0.0 and newer, you can now use several hundred APIs from newer OpenJDK versions and your app will work on any Android device? Some of these newer Java APIs in Android 11 are supported through backporting while other APIs are also available via desugaring on older devices where the Android platform does not have the APIs on the runtime.<br />
<br />
Resources:<br />
Check out the website → <a href="https://goo.gle/30FDT8S" target="_blank">https://goo.gle/30FDT8S</a><br />
Full list of supported Java 8+ APIs → <a href="https://goo.gle/3enaGD5" target="_blank">https://goo.gle/3enaGD5</a><br />
<br />
<br />Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-72532053122755628172020-05-28T17:59:00.002-07:002020-05-28T17:59:37.261-07:00What's new in Android Studio 4.0<center>
<iframe allow="accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/f1fHPqAYj5I" width="560"></iframe>
</center>
<br />
The Android Studio 4.0 release introduces a new Motion Editor, Build Speed window, Live Layout inspector, Multi Preview for your layouts, support for Kotlin DSL script files, and a Smart editor for R8 rules.<br />
<br />
The new Build Analyzer feature helps you understand and diagnose issues with your build process, such as disabled optimizations and improperly configured tasks.Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-29457332892506529052020-05-23T08:27:00.001-07:002020-05-23T08:27:35.277-07:00Virtually Maker Faire – May 23, 2020<h2><b><small>Featuring Makers Responding to COVID-19</small></b></h2><h3>24 Hours of Presentations, Workshops, Demos, and Exhibits Across All Time Zones</h3><p>Across the world, makers have responded to shortages of medical supplies and equipment with agile designs, adaptive distributed manufacturing, and community organizing. Virtually Maker Faire will be a stage to share the projects and learn from the people behind this extraordinary civic response.</p><p>Virtually Maker Faire will take place online through video sessions and an exhibit showcase on <a href="https://makeprojects.com/" target="_none">Make: Projects</a>.</p>Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-25618445530864304522020-05-19T11:52:00.000-07:002020-05-19T11:52:02.293-07:00Google Play - Spring 2020 Policy UpdatesGoogle Play PolicyBytes - Spring 2020 Policy Updates<br />
<br />
<center>
<iframe allow="accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/TDF-GvnKC18" width="560"></iframe>
</center>
<br />
explains the spring 2020 Play policy updates on subscriptions, background location access, malware, resource downloads, and more. Stay tuned to learn more about these updates, plus best practices for app compliance on Google Play and resources to help you understand the new updates.Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-8824995234217667782020-04-30T08:19:00.001-07:002020-04-30T08:34:38.733-07:00Playing Samsung Galaxy Tab S6 Lite<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjAq5ldQU1KHMa-wOeaN2slAjGu04kYWMojbMxMFLMDmRDxkFswcH450RsjXOQCvO_8oZ2evsrfwp4_daQR26do2-02vcx0_QCaIEDRuSwSBAaoQMBPxJ2VlmZ8YD6ZMvUVsKcfb4dHGek/s1600/S6Lite-001.jpg" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="772" data-original-width="1024" height="482" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjAq5ldQU1KHMa-wOeaN2slAjGu04kYWMojbMxMFLMDmRDxkFswcH450RsjXOQCvO_8oZ2evsrfwp4_daQR26do2-02vcx0_QCaIEDRuSwSBAaoQMBPxJ2VlmZ8YD6ZMvUVsKcfb4dHGek/s640/S6Lite-001.jpg" width="640" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjI7qD2H9JKNyR9EIFsKn8NkLaxJ1auW0sUh2IHMSopi0RcYPkk8MhP0-zVeB_TGrK44FlyNjqYbYix29g7swcj2XvXzgOtaufXPBgE0XiRQpODCgUvWH2VKQ9iUaQpe2aCZcqn4yHmTg0/s1600/S6Lite-002.jpg" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="772" data-original-width="1024" height="482" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjI7qD2H9JKNyR9EIFsKn8NkLaxJ1auW0sUh2IHMSopi0RcYPkk8MhP0-zVeB_TGrK44FlyNjqYbYix29g7swcj2XvXzgOtaufXPBgE0XiRQpODCgUvWH2VKQ9iUaQpe2aCZcqn4yHmTg0/s640/S6Lite-002.jpg" width="640" /></a></div>
<b><br /></b>
<b><br /></b>
<b>Samsung Galaxy Tab S6 Lite</b> is the newest tab from Samsung, is available to buy today, April 30, 2020. Running Android 10, Octa-Core (2.3GHz, 1.7GHz), 4G Ram, 10.4", 2000x1200 TFT display. Come with S Pen. You can check the full-spec here (<a href="https://www.samsung.com/uk/tablets/galaxy-tab-s6-lite/SM-P610NZBABTU/" target="_blank">https://www.samsung.com/uk/tablets/galaxy-tab-s6-lite/SM-P610NZBABTU/</a>). You have to choice your region/language on the most lower-left, different region with have slightly different configuration.<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiULYz91-ew5hDXygWYCX3wOQQK53Q5tjlFExdpsvqn2w7RZPAKFE_DmPDvmk6NoZFyO9KlJcKiXj1Mckdfkhq7g1y-PyS6HWe7366Ppy6kYhA9foilDNa0AAWAmNDRFIE-NAjol-FQww4/s1600/S6Lite+info-001.jpg" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="1024" data-original-width="621" height="640" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiULYz91-ew5hDXygWYCX3wOQQK53Q5tjlFExdpsvqn2w7RZPAKFE_DmPDvmk6NoZFyO9KlJcKiXj1Mckdfkhq7g1y-PyS6HWe7366Ppy6kYhA9foilDNa0AAWAmNDRFIE-NAjol-FQww4/s640/S6Lite+info-001.jpg" width="388" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjcEvY5-AmDbf82D_4O7V0f7a8sxnv4QxlBeFeJeVJJ4xmwqxhKQgopmUfKJiGzYe1c3QcwAOtckLA8zFHO2_-7lcD7QC4YGng0Ej8aDpW4wco1DBu932rINEnwU0zUHPrgKT2HDVon71E/s1600/S6Lite+info-002.jpg" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="1024" data-original-width="621" height="640" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjcEvY5-AmDbf82D_4O7V0f7a8sxnv4QxlBeFeJeVJJ4xmwqxhKQgopmUfKJiGzYe1c3QcwAOtckLA8zFHO2_-7lcD7QC4YGng0Ej8aDpW4wco1DBu932rINEnwU0zUHPrgKT2HDVon71E/s640/S6Lite+info-002.jpg" width="388" /></a></div>
<br />
<br />
Just buy one and play:)<br />
<br />
<b>Remote control Raspberry Pi with VNC Viewer</b><br />
<br />
<a href="https://play.google.com/store/apps/details?id=com.realvnc.viewer.android" target="_blank">VNC Viewer</a> turns the Tab S6 Lite (or other phones) into a remote desktop, remote control Mac, Windows and Linux computers (Raspberry Pi in my case) from anywhere in the world. You can view your computer's desktop remotely, and control its mouse and keyboard as though you were sitting down in front of it.<br />
<br />
This view show how Galaxy Tab S6 Lite running VNC Viewer to control Raspberry Pi Zero W. It's supposed you have already enable VNC in Raspberry Pi Configuration -> Interface, and install in tablet, and setup completely.<br />
<br />
<center>
<iframe allow="accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/qq5wDKraHWA" width="560"></iframe>
</center>
<br />
<b>Play dual Pokemon GO</b><br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiyjhreujiyT5HV_6A9aDqC0wjKTQFV_rlZ5Hc30ryequCIxRrZMvF84mxpg-CwXfpe3w6CJ7UxQlqQQz248Dm4Oseidyvqb_oE-7Qip38k60IlEDNX1phdsq0yhRxGXXL5WQbd7yCjDT0/s1600/Dual+PkGO.gif" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="720" data-original-width="1280" height="360" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiyjhreujiyT5HV_6A9aDqC0wjKTQFV_rlZ5Hc30ryequCIxRrZMvF84mxpg-CwXfpe3w6CJ7UxQlqQQz248Dm4Oseidyvqb_oE-7Qip38k60IlEDNX1phdsq0yhRxGXXL5WQbd7yCjDT0/s640/Dual+PkGO.gif" width="640" /></a></div>
<br />
<br />
Yes, you can install two copy of Pokemon Go from both Google Play Store and Samsung Galaxy Store, currently version 0.173.2-G and 0.173.2-S. Then you can run both Pokemon Go with different account at same time.<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhMdp2Mp1yzHZiKmaqhRP6KrYATDR1LXFxz32FrWNcNoopb5BDk9zjPvGVyUle3f45bCPFICvuOaN6Q_rzlTfOdc0nJG7myYvEXGOJMZvdwyHCkK7SliVfiTISXDOsihjO9VTj3gNf4QnY/s1600/S6Lite+dual+PkGO-001.jpg" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="621" data-original-width="1024" height="388" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhMdp2Mp1yzHZiKmaqhRP6KrYATDR1LXFxz32FrWNcNoopb5BDk9zjPvGVyUle3f45bCPFICvuOaN6Q_rzlTfOdc0nJG7myYvEXGOJMZvdwyHCkK7SliVfiTISXDOsihjO9VTj3gNf4QnY/s640/S6Lite+dual+PkGO-001.jpg" width="640" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEgVpdo3lpQNmKh6I9rBqJTF8Dvk2a87-se9THj_SYLOInnfMG8Yq4AWov2V6VHlw0rtcHqJsY0KDX5MguANI9SKUgsteVsKceMFQii8eExw9XG7a5ZU6lq2PjQC8aH6qAvVOSQ-qa3DXM4/s1600/S6Lite+dual+PkGO-002.jpg" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="621" data-original-width="1024" height="388" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEgVpdo3lpQNmKh6I9rBqJTF8Dvk2a87-se9THj_SYLOInnfMG8Yq4AWov2V6VHlw0rtcHqJsY0KDX5MguANI9SKUgsteVsKceMFQii8eExw9XG7a5ZU6lq2PjQC8aH6qAvVOSQ-qa3DXM4/s640/S6Lite+dual+PkGO-002.jpg" width="640" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEj9CGveV5Fxs3zjMPHmxPqjXGbS6-8CwEmfE6iADsHVuL28b_-iXCtfdLqGojV2qlQzDjZX98R-LH8yGW2SkDaCoikfMvfGemG_ogru4p6YfWGVmspW3BjiOHoo9IYN3LbzGBvuF14gB1w/s1600/S6Lite+dual+PkGO-003.jpg" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="621" data-original-width="1024" height="388" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEj9CGveV5Fxs3zjMPHmxPqjXGbS6-8CwEmfE6iADsHVuL28b_-iXCtfdLqGojV2qlQzDjZX98R-LH8yGW2SkDaCoikfMvfGemG_ogru4p6YfWGVmspW3BjiOHoo9IYN3LbzGBvuF14gB1w/s640/S6Lite+dual+PkGO-003.jpg" width="640" /></a></div>
<br />Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-85806747068751605732020-04-13T12:44:00.003-07:002020-04-13T12:44:49.772-07:00How to display layout xml in code view, for Android Studio 3.6.2With Android Studio updated (currently 3.6.2), when you view layout xml file, the original design/code option (on lower-left corner) removed. So how to view its xml code?<br />
Answer: The option is now moved to upper-right corner, you can view it in Code/Splite/Design view.<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEj5nTD37jffq4RvxWISHAS3tk-2ws2FVAZAzRXrzV3dZhV4ia7q223wNua53r7wZ0sT676bp0BufkWC2I7tp_jproM-DtldZvhi3gtM03SXH0MleEgu_IlowoqdMU8ky0y1yn8DpYDxsmA/s1600/layout+code.png" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="768" data-original-width="1366" height="358" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEj5nTD37jffq4RvxWISHAS3tk-2ws2FVAZAzRXrzV3dZhV4ia7q223wNua53r7wZ0sT676bp0BufkWC2I7tp_jproM-DtldZvhi3gtM03SXH0MleEgu_IlowoqdMU8ky0y1yn8DpYDxsmA/s640/layout+code.png" width="640" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjEqzVNyqYBveLkjgHWjlm-kt4bFQkgJu5vlJHi-jRq7t9NheBIpm52Vda4a-7soOLu_og_3tGVFTiCNvqxAR96FVTK_RFkoE_aAOH9GHZ8vclVHYhi1hgwnGenIBdJ6k9WUYURmF2Avg8/s1600/layout+splite.png" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="768" data-original-width="1366" height="358" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjEqzVNyqYBveLkjgHWjlm-kt4bFQkgJu5vlJHi-jRq7t9NheBIpm52Vda4a-7soOLu_og_3tGVFTiCNvqxAR96FVTK_RFkoE_aAOH9GHZ8vclVHYhi1hgwnGenIBdJ6k9WUYURmF2Avg8/s640/layout+splite.png" width="640" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhm36ZJ9Fc7pma9PC9xxbehxBpIyBthpCLzM2JFfFrzI1mRqfUBdVLnP-5S8QFBkaKnQe5G54ftqLTlfPclwUdgTP4TD4BTfusVDGL-esxuN1IspdRLheBLxtPs06gLVzOqtzRSKbeR0JU/s1600/layout+design.png" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="768" data-original-width="1366" height="358" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhm36ZJ9Fc7pma9PC9xxbehxBpIyBthpCLzM2JFfFrzI1mRqfUBdVLnP-5S8QFBkaKnQe5G54ftqLTlfPclwUdgTP4TD4BTfusVDGL-esxuN1IspdRLheBLxtPs06gLVzOqtzRSKbeR0JU/s640/layout+design.png" width="640" /></a></div>
<br />Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-57946324704238032342020-03-24T13:25:00.001-07:002020-03-24T13:25:23.524-07:00What's new in Android game development toolsLearn about our new development and profiling tools built specifically for Android game developers. Improve productivity with new features that allow you to build and deploy your game more efficiently, and use updated profilers to fine tune your game's performance.<br />
<br />
<center>
<iframe allow="accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/JXQBdMNDL7k" width="560"></iframe>
</center>
<br />
<b>Google for Games Developer Summit Keynote</b><br />
Game Developers Conference is one of our most anticipated times of the year to connect with the gaming industry and share our latest product updates.<br />
<center>
<iframe allow="accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/2haNNRU1Gxs" width="560"></iframe>
</center>
<br />Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-18729455068785092452020-01-19T13:43:00.004-08:002020-01-19T13:43:58.302-08:00Android-x86 - Run Android on your PC<b>Android-x86</b> is a project to port Android open source project to x86 platform. This is an open source project licensed under Apache Public License 2.0. Some components are licensed under GNU General Public License (GPL) 2.0 or later.<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhSxw-_Ws3guNwcj7nw7Q3VefagSdRrNpZa4m_mj_505ttUwrUfiVy5DX1RWel-Oi20KsetlKqW12RN7zk4AjPADo-K_Y_AFMBUUWDifgzB0sS1YNyZMggmq_GamWn7qY47jsKdYLKSzE8/s1600/Android-x86+-+Porting+Android+to+x86.png" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" data-original-height="672" data-original-width="1267" height="338" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhSxw-_Ws3guNwcj7nw7Q3VefagSdRrNpZa4m_mj_505ttUwrUfiVy5DX1RWel-Oi20KsetlKqW12RN7zk4AjPADo-K_Y_AFMBUUWDifgzB0sS1YNyZMggmq_GamWn7qY47jsKdYLKSzE8/s640/Android-x86+-+Porting+Android+to+x86.png" width="640" /></a></div>
<br />
To know more and try it, visit: <a href="https://www.android-x86.org/" target="_blank">https://www.android-x86.org/</a><br />
<br />Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0tag:blogger.com,1999:blog-89878749563391212.post-6281840209164290452019-12-19T12:26:00.000-08:002019-12-19T12:26:28.867-08:00Link your phone and Windows PC, using Microsoft Your Phone Companion app<div class="separator" style="clear: both; text-align: center;">
<a href="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhQbgJ1ZwlOQQIAOGSTnwgC0FY2uWI2hJU6Nz_GqkcBMq-SplbeojREpkghHwqD_njK-JHkbyUnz2W_pF_j-9WAD8CPdtMDYi5tJkZ4iPp9VrZ4dDe7Cdpl4uueLQRnY4B-TP8V3E3yNUM/s1600/Microsoft+Your+Phone.jpg" imageanchor="1" style="clear: right; float: right; margin-bottom: 1em; margin-left: 1em;"><img border="0" data-original-height="394" data-original-width="700" height="180" src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhQbgJ1ZwlOQQIAOGSTnwgC0FY2uWI2hJU6Nz_GqkcBMq-SplbeojREpkghHwqD_njK-JHkbyUnz2W_pF_j-9WAD8CPdtMDYi5tJkZ4iPp9VrZ4dDe7Cdpl4uueLQRnY4B-TP8V3E3yNUM/s320/Microsoft+Your+Phone.jpg" width="320" /></a></div>
With <b>Your Phone Companion</b> you can easily sync your Android phone with your Windows 10 PC. Get instant access to everything you love on your phone, right on your PC. Reply to your text messages with ease, stop emailing yourself photos, and receive your phone's notifications on your PC's bigger screen.<br />
<br />
Your Phone Companion features:<br />
<br />
Connect your phone and PC<br />
• Receive and manage your Android phone's notifications on your PC<br />
• Read and reply to your text messages from your PC<br />
• Photos taken on your phone are instantly available on your PC<br />
<br />
To use it, install <a href="https://play.google.com/store/apps/details?id=com.microsoft.appmanager" target="_blank"><b><span style="color: blue; font-family: "trebuchet ms" , sans-serif;">Your Phone Companion</span></b></a> app on your Android phone and <a href="https://www.microsoft.com/en-gb/p/your-phone/9nmpj99vjbwv" target="_blank"><b><span style="color: blue; font-family: "trebuchet ms" , sans-serif;">Your Phone</span></b></a> program on your Windows PC.<br />
<br />
<br />Erikhttp://www.blogger.com/profile/04983894331825656853noreply@blogger.com0