Monday, January 27, 2014

Android: Determine Screen Size

With the following lines of code width and height of the smartphone display can be determined under Android:
int ScreenWidth = Resources.DisplayMetrics.WidthPixels;
int ScreenHeight = Resources.DisplayMetrics.HeightPixels;

Tuesday, January 21, 2014

Thread Synchronization with AutoResetEvent

If one has multiple threads running in a program often a synchronization is needed, meaining: A thread is supposed to only continue if a specific event or similiar has occured.
To do this, one could either write an infinite loop by hand and in this way wait for the event.
But an easier and also more efficient possibility provides the class AutoResetEvent. This realizes exactly this, it provides functions with which a thread can wait for an event. When waiting the thread is blocked and eventually woken up again when the event occurs.
An instance of the class AutoResetEvent saves the current state of the event internally, in the constructor this can be initialized (false = waiting, true = event occured).
Via the function WaitOne() the current thread waits until the event occurs. This can be signaled via Set(). Reset() deletes the event then again.
In the following example the main program starts a new thread. This waits in a loop for the occurence of Event1, which is fired by a click on the button. Then a message is displayed:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Threading;

namespace ThreadSynchronization
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private AutoResetEvent Event1 = new AutoResetEvent(false);

        private void Form1_Load(object sender, EventArgs e)
        {
            Thread Thread1 = new Thread(Looper);
            Thread1.Start();
        }

        private void Looper()
        {
            while (true)
            {
                Event1.WaitOne();
                MessageBox.Show("Set");
                Event1.Reset();
            }
        }

        private void button1_Click(object sender, EventArgs e)
        {
            Event1.Set();
        }
    }
}

Wednesday, January 15, 2014

Android: Deployment failed. FastDev directory creation failed

When starting the application with the Xamarin studio sporadically the above mentioned error occurs, instead of deploying the app to the phone and starting it the following message is displayed: "Deployment failed. FastDev directory creation failed".
Luckily this error can easily be fixed: Therefor you have to deactivate under Project Options (rightclick on the project in the left panel, Options) under Build - Android Build "Fast assembly deployment".

Tuesday, January 7, 2014

Android: Save Program Data Permanently (in External Storage)

When the applications get more complex, one for sure wants to save some data permanently in the phone so they can for example be reused when next executing the program. For this Android provides essentially 2 storage areas, the Internal and the External Storage.
In the Internal Storage the data is saved such that only the application itself can access it, when uninstalling it the data is deleted automatically.
In contrast to that the External Storage is a public storage which is accessible to everyone, so also from the user from the computer for example.
The terms "internal" and "external" storage stem from the origin times of Android, where mobile phones had a small internal storage and maybe an external one in form of a SD - card for example. Today though both storages are mostly stored in the "real" internal storage of the smart phone, the difference is now just the access right.
Nevertheless it should still be checked if the External Storage is available ("mounted").
Since I had some problems with the Internal Storage and I like to be able to edit my data per hand, I mostly use the External Storage, over what I will write in this post.
So that the app is able to use the External Storage, first the permission WriteExternalStorage has to be set in the AndroidManifest.xml.
The path to the External Storage we get with Android.OS.Environment.ExternalStorageDirectory.Path.
Then we can access it like under Windows, write files etc.
In the following little sample we first check via the property ExternalStorageState, whether the External Storage is available.
Then we create the file "TestFile.txt" in the folder "ExternalStorageTest" using a StreamWriter and write a line in it. Like on Windows too all folders have to exist, therefor we check this via a Directory object and create the folder in case.
Since these things should be known from the Windows programming, here directly the complete code:
using System;
using Android.App;
using Android.Content;
using Android.Runtime;
using Android.Views;
using Android.Widget;
using Android.OS;

using System.IO;

namespace ExternalStorageExample
{
     [Activity (Label = "ExternalStorageExample", MainLauncher = true)]
     public class MainActivity : Activity
     {
          protected override void OnCreate (Bundle bundle)
          {
               base.OnCreate (bundle);

               // Set our view from the "main" layout resource
               SetContentView (Resource.Layout.Main);

               if (Android.OS.Environment.ExternalStorageState == "mounted") {
                    string Path = Android.OS.Environment.ExternalStorageDirectory.Path + "/ExternalStorageTest/";

                    if (!Directory.Exists (Path))
                         Directory.CreateDirectory (Path);

                    StreamWriter sw = new StreamWriter (new FileStream (Path + "TestFile.txt", FileMode.Create));
                    sw.WriteLine ("Test");
                    sw.Close ();
               }
          }
     }
}


Thursday, January 2, 2014

Android: Toasts

Android provides the possibilty to display so called Toasts - messages, which appear on the screen for a short time and then disappear, which looks like this:


We create a toast with the class Toast and pass the current Activity, the string to be displayed as well as the desired duration over to the creation method . For the duration we have to use the enumeration ToastLength, which contains Short and Long.
With the function SetGravity() we can set the toast's gravity as well as its offset.
With Show() we eventually display the toast:

Toast toast = Toast.MakeText(this, "Toast", ToastLength.);
toast.SetGravity(GravityFlags.Top|GravityFlags.Left, 100, 260);
toast.Show();