Aklımda Kalası Kelimeler

* давайте работать вместе
* Zarf ve Mazruf, Zerafet(xHoyratlık) ile aynı kökten(za-ra-fe) gelir
* Bedesten
* Suç subuta ermiştir - Suç sabit olmuştur

14 Ekim 2007 Pazar

Smartphone 2003 için sms kilitleme programı nasıl yazıldı... - 1 -

Geçen gün valide cep telefonum ile anneannem ile görüşmüş ama geri getirdiğinde mesajımın okunduğunu farketmiştim. Özel hayatıma bu müdahaleyi daha önceden smartlock programını motorola mpx200 cep telefonuma(smartphone işletim sistemlidir kendisi) kurarak bir süre önlemiş idim. Ama expire oldu :(

Smartphone programımı yazmak zorunda kaldığımı bu durum ile anladım ve bu işe koyuldum.Tamda Şükür Bayramınının 2. günü akşamında. Başladığımda biraz zaman alacaktı çünkü buradaki yapınının bildiklerimden ne kadar farklı ve benzer olduğunu bilmiyordum.Ben bildiğim ve yeni öğrendiğim herşeyi buraya yazacağım. Biraz bildiklerimizin zekatını vermiş olalım.

Önce basit bir smart device uygulaması buldum. Mobil cihazlarda pil durumu bilgisini alabileceğim. Buradaki yazıda geçen DLLImport, Platform Invocation nedir diye bir öğrenelim biliyorsak hatırlayalım.

Öncelikle VC++ ile yazılmış bazı kütüphanelerin C# içinde kullanılması gerekecek.Buna platform invoke diyoruz. Win32 apilerinin C# içinde kullanımı ile ilgili güzel bir makale var csharpnedir.com adresinde.Bu makale ve başka yerli yabancı makalelerden alıntılar ile anlatımıma devam edeceğim.

Win32 sistem fonksiyonları kullanıldığında, kod CLR tarafından yönetilmekten çıkar. .NET ortamında geliştirilen bir uygulamada yönetilmeyen kod segmenti ile kaşılaşılırsa ilgili kod segmenti CLR tarafından yönetilmekten çıkar. Dolayısıyla "garbage collection" mekanizması ve .NET'e özgü diğer servisler kullanım dışı olur.

Tabii unmanaged kodlar daha hızlı çalışmasını sağlar.

CLR tarafından yönetilmeyen kodlara erişebilmek için C#'ta System.Runtime.InteropServices isim alanında bulunan ve DllImprtAttribute sınıfını temsil eden DllImport niteliği kullanılmaktadır. DllImport niteliği ile harici bir kaynakta bulunan metoda referans vermek için external anahtar sözcüğü kullanılır. Bir sınıf bildiriminin en başında external anahtar sözcüğü ve DllImport niteliği kullanılarak CLR tarafından yönetilmeyen bir metot bildirimi yapılır. Tabi metodun gövdesi harici bir kaynakta zaten var olduğu için bizim metodun gövdesini yazmamızın bir anlamı yoktur. Ardından bu metot sınıfın istenildiği yerinde kullanılabilir. İsterseniz basit bir örnekle DllImport niteliğinin kullanımını gösterelim.

Win API(Application Interface) windows sistemlerinin programlanabilir arayüzünü içermektedir. Windows uygulamarının tamamı bu arayüzdeki fonksiyonları ve diğer yapıları kullanmaktadır. Aşağıdaki programda Win32 sistemlerinde bulunan MessageBox() fonksiyonunun kullanımına bir örnek verilmiştir.




using System;
using System.Runtime.InteropServices;
class Class1
{
[DllImport("user32.dll")]
public static extern int MessageBox(int tip,string mesaj,string baslik,int secenek);
static void Main()
{
MessageBox(0,"Mesaj","Win API MessageBox",2);
}
}



DllImport Attribute sınıfının bir tane yapıcı metodu bulunmaktadır. Bu metot parametre olarak harici kaynağın adı belirtmektedir. Yukarıdaki kaynak kodda MessageBox fonksiyonunun bulunduğu "user32.dll" isimli dosya DllImport niteliğine parametre olarak verilmiştir. Bu örnekte dikkat edilmesi gereken diğer nokta ise extern anahtar sözcüğünün kullanımıdır. Bu anahtar sözcük ile bildirimi yapılan metodun harici bir dosyada olduğu belirtilmektedir. Dolayısıyla C# derleyicisi metodun gövdesini kaynak kodda aramayacaktır.


Gövdesi yüklenmeyen metod belleğe yüklenir ve bellekteki metodun başlangıç adresi saklanır.DLLIMPORT ve WinAPI kullanımı makalede daha detaylı anlatılmıştır, okumanızı şiddetle tavsiye ederim.

Microsoft bize bir aygıtın güç durumunu nasıl öğrenebileceğimizi C# kodu ile anlatmış.
Biz buradaki yazıyı biraz inceleyeceğiz. P/Invoke ile SYSTEM_POWER_STATUS_EX sınıfı pil ve enerji durumu bilgileri ile dolacak ve bu bilgileri formumuzun üzerinde progressbar bileşeni ile göstereceğiz.
SYSTEM_POWER_STATUS_EX sınıfı tabii smartphone üzerine yazdığımız için SDK Documentation for Windows Mobile-Based Smartphones başlığından takip edilecek.


typedef struct _SYSTEM_POWER_STATUS_EX {
BYTE ACLineStatus;
BYTE BatteryFlag;
BYTE BatteryLifePercent;
BYTE Reserved1;
DWORD BatteryLifeTime;
DWORD BatteryFullLifeTime;
BYTE Reserved2;
BYTE BackupBatteryFlag;
BYTE BackupBatteryLifePercent;
BYTE Reserved3;
DWORD BackupBatteryLifeTime;
DWORD BackupBatteryFullLifeTime;
} SYSTEM_POWER_STATUS_EX, * PSYSTEM_POWER_STATUS_EX, * PSYSTEM_POWER_STATUS_EX;


typedef struct _SYSTEM_POWER_STATUS_EX ile öncelikle bir yapı(pascaldaki record gibi) tanımlıyoruz. Bu yapının 12 değişkeni var ve bu değişkenler bizim istediğimiz pile ait bilgiler ile dolacak.

Örneğin:
ACLineStatus BYTE tipinde değer alıyor ve bize AC güç durumunu gösterecek.Değerleri aşağıdadır.
Değer -- Tanımı
0 -----> Offline
1 -----> Online
2 -----> Backup power
255 ---> Unknown status


Visual Studio ile SmartPhone için bir proje başlatıyoruz. C# dili kullanarak yazacağız.

GetSystemPowerStatusEx bize pil bilgilerini getirecek fonksiyondur ve coredll içerisinde yer almaktadır.

Smartphone işletim sistemindeki "coredll" dllini P/Invoke ile kullancağız.

Formun ü zerine iki textbox bileşeni koyarak şarj edilme durumunu ve pilin kalan enerjisinin yüzde olarak değerini Text değerlerine yazacağız.

Bunun için önce coredll içerisinde tanımlı "typdef struct SYSTEM_POWER_STATUS_EX" diye tanımlı değişkeni (pil bilgilerinin döndürüleceği struct tipinde değişkendir) sınıf olarak tanımlamalıyız.

[DllImport( "coredll" )]
public static extern uint GetSystemPowerStatusEx( SYSTEM_POWER_STATUS_EX lpSystemPowerStatus, bool fUpdate );
Yukarıda extern, DllImport ile ilgili bilgiler verilmişti.Biz GetSystemPowerStatusEx metoduna, SYSTEM_POWER_STATUS_EX sınıfının bir örneğini ve anlık donanım bilgisi isteyip istemediğimizi bildiren bool değerini göndermeliyiz.


public class SYSTEM_POWER_STATUS_EX
{
public byte ACLineStatus;
public byte BatteryFlag;
public byte BatteryLifePercent;
public byte Reserved1;
public uint BatteryLifeTime;
public uint BatteryFullLifeTime;
public byte Reserved2;
public byte BackupBatteryFlag;
public byte BackupBatteryLifePercent;
public byte Reserved3;
public uint BackupBatteryLifeTime;
public uint BackupBatteryFullLifeTime;

[DllImport( "coredll" )]
public static extern uint GetSystemPowerStatusEx( SYSTEM_POWER_STATUS_EX lpSystemPowerStatus, bool fUpdate );
}


Buraya kadar kullanacağımız sınıf ve P/Invoke metodumuz tanımlandııı...
Şimdi sol düğmeye(Soft Key1) bastığımızda aşağıdaki kodlarımızı işletmeliyiz. Bu koda göre SYSTEM_POWER_STATUS_EX tipinde bir instance(nesne) oluşturuyor ve SYSTEM_POWER_STATUS_EX.GetSystemPowerStatusEx() metodumuza parametre olarak gönderiyoruz. Bu nesne pil durumu bilgisi ile doldurularak bize geri gönderiliyor.Bu nesnenin içindeki değişkenlerin değerlerinden "BatteryLifeTime" ve "BatteryFlag" değişkenlerinin değerlerini TextBox bileşenlerinin Text özelliklerine yazıyoruz.


private void menuItem1_Click( object sender, EventArgs e )
{
SYSTEM_POWER_STATUS_EX pilDurumu = new SYSTEM_POWER_STATUS_EX();
if ( SYSTEM_POWER_STATUS_EX.GetSystemPowerStatusEx( pilDurumu, true ) == 1 )
{
float f_kalanDakika = pilDurumu.BatteryLifeTime / 3600;
txt_lifeTime.Text = f_kalanDakika.ToString();

Hashtable hsh_sarjDurumu = new Hashtable();
hsh_sarjDurumu.Add( "1", "Yüksek" );
hsh_sarjDurumu.Add( "2", "Düşük" );
hsh_sarjDurumu.Add( "4", "Kritik Seviye" );
hsh_sarjDurumu.Add( "8", "Şarj ediyor" );
hsh_sarjDurumu.Add( "128", "Sistem Pili Yok" );
hsh_sarjDurumu.Add( "255", "Bilinmeyen Durum" );
txt_sarjDurumu.Text = hsh_sarjDurumu[ pilDurum.BatteryFlag.ToString() ].ToString();
}
}



Buraya kadar pil durumunu gösteren program ile smartphon'umuza başlangıç yaptık.
Bakalım devamı gelecek mi :)

Hiç yorum yok: