Windows Phone 8 ve Azure Mobil Servisler

Oldukça uzun zamandır (yaklaşık 4 ay 🙂 ) işe başlamış olmam ve okulumun hala devam ediyor olmasından dolayı yazamıyorum. Umuyorum bundan sonra daha çok yazma fırsatı bulabilirim. Bu yazımda aslında MSP olduğum dönemde hazırlamış olduğum Windows Phone 8 ve Azure Mobil Servisleri anlatan video kaydını paylaşacağım. Öncelikle diğer arkadaşlarında hazırlamış olduğu videoları birleştirip Youtube’a yükleyen eski MSP Lead’im ve şu anda ki iş arkadaşım Fatih Bekdemir’e teşekkür ederim. Benim hazırlamış olduğum bölüm uzun bir serinin 24. bölümüdür, tüm playlist’e

http://www.youtube.com/watch?v=CXNhanNPmA8&list=PL9ReGaZDkswEswygAyOTeU1r-DWsTDzO-&index=24

linkinden erişebilirsiniz. Bir sonraki yazımda görüşmek üzere…

Windows Phone ScrollViewer bug

Bir kaç gün önce üzerinde çalıştığım projede DataTemplate içerisindeki kontrollere drag and drop eklemekle uğraşırken beni oldukça uğraştıran bir problem ortaya çıktı. Drag&Drop özelliği eklediğim kontrolleri item’ın grid’ine ait hold eventiyle tuttuktan sonra ManipulationDelta event’inde sürükleme işlemini gerçekleştirirken listbox’a ait ScrollViewer’ı disabled etmiş olmama rağmen kontrol scroll yapmaktaydı. Daha sonradan farkına vardığım bir şey ise, ScrollViewer.VerticalScrollBarVisibility özelliğini ScrollBarVisibility.Disabled olarak atanmış olmasına rağmen listbox üzerinde hold eventi gerçekleştikten sonra bu Scroll’un çalışıyor olması oldu.  Bu arada DataTemplate içerisindeki bir kontrolün listbox’ın dışarısına nasıl sürükleneceği ile ilgili başka bir yazı daha sonra ekleyeceğim.

öncelikle ister Xaml’da listbox’ın ScrollViewer.VerticalScrollBarVisibility‘sini false yapın veya kod tarafında listbox’ın SetValue metodunu SetValue(ScrollViewer.VerticalScrollBarVisibility,ScrollBarVisibility.Disabled) sonuç değişmemekte ve hold eventi çalıştıktan sonra listbox scroll edilebilmekte. Bunun için ben aşağıdaki gibi bir extension method oluşturdum ve scroll’un manipulation modu’nu sistem düzeyinde yapmaktansa kontrol düzeyinde yapmasını sağladım. Ancak scrollun düzgün bir şekilde çalışması için ManipulationMode’un daha sonradan tekrar sisteme verilmesi daha iyi olacaktır.

public static void SetListBoxScrollStatus(ListBox lb, ScrollBarVisibility horizontalVisibility, ScrollBarVisibility verticalVisibility)
{
    //listbox'a ait scrollviewer alınıyor
    ScrollViewer myScrollviewer = VisualTreeHelper.GetChild(lb, 0) as ScrollViewer;

    myScrollviewer.HorizontalScrollBarVisibility = horizontalVisibility;
    myScrollviewer.VerticalScrollBarVisibility = verticalVisibility;

    if ((horizontalVisibility | verticalVisibility) == ScrollBarVisibility.Disabled)
        //scrollviewer'lardan herhangi bir tanesi disabled ise
        myScrollviewer.SetValue(ScrollViewer.ManipulationModeProperty, ManipulationMode.Control);
    else
        //scrollviewerlar enabled ise
        myScrollviewer.SetValue(ScrollViewer.ManipulationModeProperty, ManipulationMode.System);
}

Şimdilik çözüm yolu bu kadardır. Umuyorum kısa bir süre sonra listbox itemlarına nasıl drag&drop özelliği ekleyebileceğinizle ilgili bir başka yazı yazacağım.

Azure ve Windows Phone push Notifications

Tüm takipçilerime ve ilk kez bu yazımı okuyacak olanlara merhabalar, bu yazımda Microsoft Azure ve Windows Phone 8 için push notificationlarının nasıl oluşturulacağından bahsetmek istiyorum.

Minimum gerekenler,

  • Windows Phone 8 SDK,
  • Windows Azure Hesabı

Windows Azure hesabı olmayanlar ve ilk kez denemek isteyenler ücretsiz 90 günlük deneme sürümüne http://www.windowsazure.com/en-us/ adresinden üye olabilirler.

Azure Mobil Servisleri

Öncelikle Azure yönetim portalından yeni bir mobil servis oluşturarak işlemimize başlıyoruz.

1

Yukarıdaki ekran görüntüsünde de görüldüğü üzere Compute>Mobile Service>Create dememiz bu işlem için yeterli olacaktır.

2

Karşımıza gelen bu yeni Create a Mobile Service ekranındaki formu doldurmamız gerekiyor, URL kısmı mobil servisiniz için bir web adresi olacaktır yani ekran görüntüsüne bakıldığına pushdeneme.azure-mobile.net bizim web adresimiz. Push servisleri kullanabilmemiz için birde veritabanına ihtiyacımız olacağından Create a new SQL database instance diyoruz. Region kısmında ise veritabanımızın hangi datacenter’da tutulmasını istediğimizi belirtmemiz gerekiyor.

3

Bu kısımda veritabanımızı oluşturmamız gerekiyor, Eğer daha önceden azure kullandıysanız ve bir veritabanınız mevcut ise bunu seçerek devam edebilirsiniz yada eğer yeniyseniz yeni bir veritabanı oluşturarak bu işlemleri tamamlayabilirsiniz.

Yukarıdaki işlemleri tamamladıktan sonra, uygulamamızın kullanacağı mobil servisini ve veritabanını oluşturduk. Şimdi sıra uygulamamızı oluşturmaya geldi.

4

Bundan sonrasında azure’un örnek olması açısından kullanıcılarına sunmuş olduğu hazır örneği kullanarak devam edeceğim, mobil servisi oluşturduktan sonra karşınıza yukarıdaki gibi bir ekran gelecektir. Eğer herhangi bir dashboard’la karşılaşacak olursanızda üst menüdeki dashboard seçeneğinin hemen yanında bulunan bulut ikonuna tıklamanız yeterlidir. Yukarıdaki ekrandan create a new windows phone app diyerek uygulamamıza devam edebiliriz.

5

Bu ekranda ise azure’un bize sadece bu örnek için sunmuş olduğu sihirbazı kullanarak Create TodoItem Table ile veritabanımızda uygulamamız için bir bir tablo oluşturacağız. Yazıyı uzatmak istemediğim için detaylı olarak azure veritabanından bahsetmek istemiyorum. Bu yüzden mümkün olduğunca kolay şekilde uygulamamızı yapacağız. Tablomuzu’da oluşturduktan sonra Download diyerek uygulamamızın hazır C#/Xaml kodunu indirip Visual Studio ile açabiliriz.

Şu an daha fazla devam etmeden önce burada bahsetmek istediğim bir önemli nokta var, uygulamamız azure ile nasıl iletişim kuracak. Solution explorer’dan App.xaml.cs kodunu açtığınızda farkederseniz böyle bir kod göreceksiniz.

public static PhoneApplicationFrame RootFrame { get; private set; }

        public static MobileServiceClient MobileService = new MobileServiceClient(
            "mobile-servis url'i",
            "app-key"
            );

bu kod bloğunda uygulamamıza ait url’i ve app-key’i belirtmemiz gerekiyor. Appkey’inizi diğer uygulamalarınızda öğrenmek istersenizde Get Started ekranından CONNECT AN EXISTING WINDOWS PHONE 8 APP dedeğinizde karşınıza gelen ekrandan görüntüleyebilirsiniz.
6Artık uygulamamıza ait push notificationlarımızı oluşturabiliriz.

App.xaml.cs dosyasında global olacak şekilde aşağıdaki objeyi yaratın

public static HttpNotificationChannel CurrentChannel { get; private set; }

Daha sonrasında ise Push notificationlarımız için bir channel oluşturmamız gerekiyor. Bunun içinde aşağıdaki methodu tanımlamanız yeterli olacaktır.

private void KanalOlustur()
{
    CurrentChannel = HttpNotificationChannel.Find("MyPushChannel");

if (CurrentChannel == null)
{
    CurrentChannel = new HttpNotificationChannel("MyPushChannel");
    CurrentChannel.Open();
    CurrentChannel.BindToShellTile();
}

}

Yukarıdaki kodun son satırında BindToShellTile’ı görmüşsünüz. Bu uygulamamızın shellTile notificationlarını kullanacağını belirtmektedir. Eğer bir toast kullanmak istiyorsanızda bu kısmı aşağıdaki gibi değiştirebilirsiniz.

CurrentChannel.BindToShellToast();

Şimdi ise sırada uygulamamız açıldığında bu methodu tetikleyecek olan kod bloğunu yazmak olucak. App.xaml.cs dosyasında Application_LaunchingEvent handler’ını bularak oluşturmuş oluduğunuz KanalOlustur methodunu çağırmanız yeterlidir. Bu işlemlerden sonra Application_Launching event handlerı aşağıdaki gibi görünecektir.

private void Application_Launching(object sender, LaunchingEventArgs e)
        {
            AcquirePushChannel();
        }

Kodumuzda son olarak yapmamız gereken ise herhangi bir push notification göndermek istediğimizde göndermek istemiş olduğumuz notification kanalınıda belirtmemiz gerekmektedir. MainPage.xaml.cs dosyasını açtığınızda sınıfın en başındaki entity sınıfını görmüş olmanız gerekmektedir. Bu sınıfa aşağıdaki özelliği eklediğinizde artık azure servisimize veri gönderirken push kanalımızda göndermiş olacağız.

[DataMember(Name = "channel")]
 public string Channel { get; set; }

Artık son olarakta uygulamamızdan notificationlarımızı gönderme kodumuzuda ekleyip bu kısmı tamamlayabiliriz. Buton1_click eventine geldiğinizde bir InsertTodoItem satırının olduğu gözünüze çarpacaktır. Bu satırda listemize eklemiş olduğumuz elemanlar mobil servisimize ait veritabanında tutulmaktadır. burada bizim yapmamız gereken değişiklik aşağıdadır. Basitçe yapılacak öğemizi azure servisimize gönderirken yanında push kanalımızıda göndermekteyiz.

private void ButtonSave_Click(object sender, RoutedEventArgs e)
        {
            var todoItem = new TodoItem { Text = TodoInput.Text, Channel=App.CurrentChannel.ChannelUri.ToString() };
            InsertTodoItem(todoItem);
        }

Şimdilik uygulamamızın kaynak koduyla işimiz bitti, artık azure veritabanımızı push notification göndermesi için ayarlayabiliriz. Bunun için üstte yer alan menüden önce Data’yı daha sonrasında ise tablonuzu seçiniz.

7

Karşınıza gelen ekran size tablonuzda herhangi bir veri olmadığını söylemektedir, henüz data göndermedik. Yine üstteki menüden Script’i seçerek, veritabanımıza herhangi bir veri girildiğine yapılacak olan işlemi belirtmemiz gerekiyor. Amacınız sadece veriler üzerinde ekleme,silme, okuma veya güncelleme yapmak ise burada herhangi bir değişiklik yapmanıza gerek yoktur. Biz bir push notification göndereceğimiz için insert fonksiyonunda aşağıdaki değişikliği yapmamız gerekiyor.

function insert(item, user, request) {
    request.execute({
        success: function () {
            // Write to the response and then send the notification in the background
            request.respond();
            push.mpns.sendFlipTile(item.channel, {
                title: item.text
            }, {
                success: function (pushResponse) {
                    console.log("Sent push:", pushResponse);
                }
            });
        }
    });
}

Uygulamınızda tile notification yerine toast göstermek istiyorsanızda yukarıdaki javascript kodunun yerine aşağıdakini kullanabilirsiniz.

function insert(item, user, request) {
request.execute({
        success: function(){
            request.respond();
            push.mpns.sendToast(item.channel,{text1:'You have new message',
            text2:item.message,param:'/SendMessage.xaml?receiver='+item.sender},{
                success:function(pushResponse){

                      console.log("Sent push:",pushResponse)
            }
    });
        }
    });
}

Evet, sonunda uygulamamızı ancak tek bir eksiğimiz kaldı, oda tabiki de uygulamamıza push notificationlarını kullanacağını belirten izinleri ayarlamak. Visual Studio Solution Explorer’dan Properties -> WMAppManifest.xml dosyasını açarak arayüzden Capabilities’i seçiniz.

8

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

Şimdi F5’e basarak uygulamanızı kontrol edebilirsiniz. Ancak uygulamadan bir push notification göndermeden önce Tile eklemeyi unutmayın. Bu konuyla ilgili herhangi bir sorusu olanlar yazının altındaki yorum kısmını kullanabilirler.

Bir sonraki yazımda görüşmek üzere.

Not: Uygulamadaki kodların bazı kısımları, http://www.windowsazure.com’dan alınmıştır.

Demola Network Tanıtımı ve Windows Phone Eğitimi – İzmir

Blog’umu takip edenlerden uzun bir süredir yeni yazı yayınlıyamadığım için öncelikle özür dilerim. Şu sıralar vizelerdi, projelerdi, etkinliklerdi derken fazla bir vaktim olmadı.

Bu yazımda teknik konulardan bahsetmekten ziyade İzmir Üniversitesi ve Dokuz Eylül Üniversitesi ile birlikte ortaklaşa düzenlenen bir etkinlikten bahsetmek istiyorum. Geçtiğimiz 10 Nisan günün İzmir Üniversite’sinde Demola Network’ün sunmuş olduğu bir etkinlik gerçekleşti. Hemen arkasından da 11-12 Nisan günlerinde yine Demola’nın katkısıyla Windows Phone 8 eğitimi Dokuz Eylül Üniversitesi’nde yapıldı. Peki biraz Demola’dan bahsetmek gerekirse, nedir bu demola?

Demola Network, Demola 2008 yılında Finlandi’yanın Tampere kentinde kurulmuş olan bir firmadır. Amaçları üniversiteler ile endüstriyi ortak projelerde çalışmaları için birleştirmektir. Kendilerine üye olan olan şirketler arasında Nokia’da bulunmaktadır. Demola’nın kurmuş olduğu sistem endüstriden gelen bir projeyi öğrencilere sunarak ilgili proje ile ilgili olarak öğrencilerin çözüm bulmalarını sağlamaktadır. Bu sayede şirketler kaynak ayıramadıkları projeleri çöpe atmaktansa Demola’nın sunmuş olduğu büyük bir öğrenci kütlesi sayesinde bu projeleri gerçekleştirebilmektedirler. Öğrencilere katkıları ise, bilindiği gibi üniversitelerin en büyük problemi teorik eğitimlerin iş yaşamına fazla uymuyor olması. Ancak Demola’nın sunmuş olduğu bu sistem sayesinde öğrenciler gerçek hayattaki projelerde çalışarak deneyim kazanmakta ve mezun olduklarında sadece teorik bilgileriyle değil, aynı zamanda iş yaşamında da kazanmış oldukları deneyimlerle mezun olmaktadırlar.

Demola’nın 10 Nisan gününde gerçekleştirmiş olduğu sunuma katılım oldukça güzeldi katılımcılar arasında Netsis, Ege-Binom, Vestel, Giltaş gibi Ege Bölgesindeki büyük firmalarda yer almaktaydı. Demola’dan gelen Ville Kairamo ve Harri Pennanen’ın sunumlarının arkasından firmalar kendi aralarında böyle bir sistem Ege Bölgesinde ve Türkiye’de nasıl yararlı olabilir, problemleri nelerdir şeklinde birde bir workshop gerçekleştirdiler.

10-11 Nisan günlerinde ise sabırsızlıkla beklemiş olduğum Windows Phone Eğitimi Dr. Michael Samarin, Futurice Ltd tarafından gerçekleştirildi.

20130411_094656

Eğitimin ilk gününde Nokia Developer Consultancy’nin uygulama geliştiricilere ne gibi özellikler sunduğunu ve windows phone 7 ile windows phone 8 arasındaki farklardan bahsedildi. Nokia gerçekten de uygulama geliştiriciler için oldukça güzel özellikler sunmakta ki bunlardan birisi Uzaktan Cihaz erişimi. Bu sistem sayesinde Nokia Developer Consultancy üyeleri uygulamalarını gerçek cihazlar üzerinde uzaktan erişim ile test edebilme imkanlarına sahip oluyorlar. Peki nasıl Nokia Developer Consultancy üyeliği alınabileceğine gelince Nokia 99$ karşılığında 1 yıllık üyeliği uygulama geliştiricilere sunmakta. Windows Phone 8 ile ilgili olarak Live Tile’lar, Push Notification’lar, People Hub gibi özelliklerden bahsedildi.

Eğitimin ikinci gününde ise artık uygulamaları emulatör üzerinde değilde gerçek cihazlar üzerinde denemeye başladık. Bu günde Windows Phone 8 ‘in camera, NFC, bluetooth, AppToApp Communication gibi API’ları tanıtıldı.

Yazımda aslında eğitimin tamamını anlatmak isterdim fakat 2 günlük bu süreç oldukça yorucu ve güzel geçti, tamamını burada yazmam pekte mümkün değil. Ancak İzmir’de böyle bir etkinliğin gerçekleşmiş olması oldukça güzel bir çalışmaydı.

Bu konuda İzmir Üniversitesi ve Dokuz Eylül Üniversitesine teşekkürlerimi sunarım. Başka bir yazıda görüşmek üzere

Demola Network ile ilgili daha detaylı bilgi almak isteyenler

http://demola.fi/ bu adresten yararlanabilir.

Windows 8 Hyper-v ve Sanallaştırma (Ubuntu Sanal Makine Kurulumu)

Başlangıçta bu yazıyı yazıp yazmamakta oldukça kararsızdım. Eski deneyimlerime göre hiçbir zaman tek bir işletim sisteminin üzerinde ikinci bir sanal makine çalıştırma fikrine ısınamamıştım. Tabi buda beni sürekli bilgisayarımı yeniden başlatıp işletim sistemi değiştirmeye zorluyordu. Eğer sizde iki işletim sisteminde çalışmak zorundaysanız ve sürekli bilgisayarınızı yeniden başlatıp işletim sistemi değiştirmekten sıkıldıysanız. Size Hyper-V’yi kesinlikle denemenizi öneririm. Bu yazımda da Hyper-V’ye nasıl Ubuntu 12.04 yükleyebileceğinizi anlatacağım. Neden Ubuntu diye sorarsanız, açıkçası bu yazıyı yazarken aynı zamanda da projemde Ubuntu kullanmam gerektiğinden dolayı tercihim bu yönde oldu. Fakat dilerseniz farklı işletim sistemleride kurabilirsiniz. Süreç oldukça benzer işleyecektir. Daha öncede belirttiğim gibi işleme başlamadan önce lütfen aşağıdaki sistem gereksinimlerine dikkat ediniz.

-64-bit CPU
-Intel VT veya AMD-V işlemcinizde çalışır durumda olmalı
– SLAT(Second level address translation) desteği. Daha fazla bilgi için buraya göz atabilirsiniz.
– En az 4GB Ram
– Windows 8 Pro lisansı.

Öncelikle Hyper-V eğer sisteminizde etkin durumda değil ise, etkinleştirmek için lütfen bu video’ya izleyebilirsiniz.

Bu aşamadan sonra sisteminizin minimum gereksinimleri karşıladığını ve Hyper-V’yi sisteminizde etkinleştirdiğinizi varsayıyorum.

Hyper-V Yeni Sanal Makine Oluşturma

Öncelikle Hyper-V Manager’ı yönetici modunda çalıştırın. Bu aşamada herhangi bir problemle karşılaşmamanız için anti-virüs programınızı kısa bir süreliğine kapatmanızı öneririm.

1- Sağ tarafta bulunan New->Virtual Machine(Yeni->Sanal Makine) seçeneğini seçiniz.

1

Karşınıza aşağıdaki gibi bir ekran gelecektir. İleri diyerek bu ekranı geçelim.

2

2- Bu ekranda sizden sanal makinenize bir ad vermeniz istenecektir. Dilediğiniz gibi bir isim verebilirsiniz. Farkettiyseniz aşağıda birde sanal makinenizi farklı bir konuma depolamak isterseniz diye birde seçenek var. Eğer böyle bir isteğiniz varsa kutuyu işaretleyip daha sonrasında depolamak istediğiniz konumu seçmeniz yeterli olacaktır.

3

3- Sanal makinemizi isimlendirdikten sonra şimdi oluşturduğumuz sanal makineye kullanması gereken bellek miktarını belirlememiz gerekmekte. Eğer sistem belleğiniz yüksekse bunu 4GB gibi bir miktar belirleyebilirsiniz yada benim gibi 2GB’la da yetinebilirsiniz.

4

4-Bu aşamada ise sanal makinenizin ağa nasıl bağlantı kuracağını belirlemeniz gerekmekte. Bu ekranda hangi bağlantı türünü kullanmak istediğinize karar vererek devam ediniz.

5

5-Sıra geldi sanal makinemize sabit disk oluşturmaya, bu aşamada eğer önceden oluşturmuş olduğunuz bir sanal disk yoksa default olarak seçili olan Sanal sabit disk oluştur seçeneğini işaretli bırakın ve Boyut olarakta sanal makinenizin ne kadarlık bir disk alanına ihtiyaç duyacağına karar verip girdikten sonra ileri diyebilirsiniz. Ben burda sadece işletim sistemini kullanacağım için 15GB gibi bir alan ayırdım.

6

6- Son aşamamızda ise işletim sistemini nereden yükleyeceğimizi belirtmemiz gerekiyor. Eğer bir kurulum diskine sahipseniz disk sürücünüzün ismini göstermeniz yeterli olacaktır. Eğer bir *.iso dosyasından yükleme yapmak istiyorsanız *.iso dosyasının bulunduğu yeri göstermeniz gerekecektir.

7

7- Son aşamada bize oluşturmuş olduğumuz sistemin bir özeti gösterilecektir son’a tıklayarak sanal makinenizi oluşturabilirsiniz.

NOT: Eğer bu aşamada Synthetic Disk Drive eklenemedi gibi bir hata alacak olursanız buna kullanmış olduğunuz anti-virüs programı neden oluyor olabilir. Devre dışı bırakarak tekrar deneyin. Bende bu sorun bundan kaynaklanmıştı.

Sanal Makineye Ubuntu Yükleme

Yukarıdaki adımları tamamladıktan sonra şimdi sanal makinemizi sağ tarafta bulunan menüden Start(Başlat) butonuna tıklayarak başlatın ve Connect(Bağlan)’a tıklayarak sanal cihazınızı başlatınız.

8

NOT: Bu aşamada eğer bir yükleme diskinden yükleme yapacaksanız diskin bilgisayarınıza takılı olduğundan emin olun.

Bu aşamadan sonra artık her adımı tek tek anlatmayacağım ekrandaki yönergeler oldukça basit. Sadece önemli noktaları belirteceğim.

9

1- Yukarıdaki ekran geldiğinde kullanmak istediğiniz dili seçip Install demeniz yeterli olacaktır.

2- Karşınıza gelen bir sonraki pencerede continue diyerek devam ediniz.

3- Şimdiyse ubuntu installer bizden yükleme tipini belirlememizi istemekte bu aşamada default olarak seçili olan seçenekle devam edip kolay kurulumu gerçekleştirebilir veya diğer seçeneği seçerek sanal disk üzerinde bölme, silme vs. işlemler gerçekleştirebilirsiniz.

11

4- Bu aşamadan sonra ise ekrandaki yönergeleri takip etmeniz yeterli olacaktır.

Umarım bu yazım sizlerinde Hyper-V kullanarak bilgisayarınızda sanallaştırma yapmanıza yardımcı olacaktır. Yukarıda da belirttiğim gibi sanal makinenize sadece Ubuntu veya herhangi bir Linux dağıtımı kurmak zorunda değilsiniz, eğer gerekli lisanslara sahipseniz ihtiyacınıza göre Windows 7, Windows Server 2008, 2012 vs. seçebilirsiniz.

Bir sonraki yazımda görüşmek üzere

12

ASP.NET MVC 4 ile OpenTok API Version 2.0 Kullanımı

Uzun bir süredir, live video streaming (canlı video yayını)’i bir ücretsiz bir media server üzerinde nasıl kullanabileceğimi araştırıyordum ve OpenTok API ile tanıştım. Amacım OpenTok API’yi kullanarak şu an çalıştığım bir ASP.NET MVC 4 projesinde live video streaming gerçekleştirebilmekti. Uzun arayışlarım sonucunda ne yazıkki hiçbir tutorial’a rastlayamadım ve en sonunda kendim bir tane yazmak istedim. Bu yazımda ASP.NET MVC 4, JavaScript ve OpenTok API kullanarak nasıl bir live video streaming web sayfası geliştirmeyi anlatıcam.

Bu yazıda ilerlemeden önce lütfen aşağıdaki gereksinimleri sağladığınızdan emin olunuz.

Visual Studio 2012 veya Visual Studio 2010 bu linki takip ediniz.

OpenTok .NET API

Ben yazımda Visual Studio 2012 kullanıcam.

1. Yeni Proje Başalatınız

Adsız

2. Açılan pencereden ASP.NET MVC4 Web Application’ı seçerek, projenize dilediğiniz adı verebilirsiniz.

3. Ok dedikten sonra karşınıza Project Template penceresi açılacaktır.

Adsız2

4. Bu pencereden Internet Application’ı ve View Engine olarakta Razor’ı seçerek Ok’e basın.

5. Projemizi oluşturduktan sora sıra geldi Web.Config dosyasında yapıcağımız ayarlara, öncelikle kullanacağımız database için connection string’imizi ayarlayarak başlayalım.

<add name="SessionsEntities" connectionString="Data Source=|Data Directory|Session.sdf" providerName="System.Data.SqlServerCe.4.0" />

6. Şimdi yapmamız gereken ise OpenTok API için gerekli olan ayarlamaları yapmaya. Öncelikle bunu yapmak için OpenTok web sayfasına giderek kayıt olmanız gerekmektedir. Sayfaya kayıt olduktan sonra TokBox size bir Api Key ve Secret verecektir.
7. Sırada web.config dosyamızda OpenTok API’yi ayarlamaya geldi

  <appSettings>
    <add key="opentok_key" value="***API Key***" />
    <add key="opentok_secret" value="***API Secret***" />
    <add key="opentok_server" value="https://api.opentok.com" />
    <add key="opentok_token_sentinel" value="T1==" />
    <add key="opentok_sdk_version" value="tbdotnet" />
  </appSettings>

8. Gerekli ayarlamalarımızıda yaptıktan sonra artık geliştirmeye başlayabiliriz.
9. Projenize sağ tıklayıp Add->Existing Item’ı seçiniz.
10. Daha önceden bu adresten indirmiş olduğunuz .NET API’yi seçerek projenize ekleyeniz.
11. API’yi projeye ekledikten sonra artık Model’imizi oluşturabiliriz.
12. Yine Models klasörüne sağ tıklayarak Add->Class’ı seçerek iki yeni class oluşturunuz, ve ilkini Sessions olarak diğerinide SessionsEntities olarak adlandırınız.
13. Şimdi Sessions classına girerek aşağıdaki modeli oluşturunuz.

public class Sessions
 {
 [Key]
 public int SessionId { get; set; }
 public string SessionName { get; set; }
 public string SessionToken { get; set; }
 }

Bu modelimizde SessionId veritabanımız için gerekli olan primary key iken, SessionName ve SessionToken ise OpenTok APIile oluşturacağınız sessionları ve tokenları tutacak olan alandır.

14. SessionEntities Class’ına girerek oluşturduğunuz tablonun DbContext’ini aşağıdaki gibi yaratın.


public class SessionEntities:DbContext
 {
 public DbSet<Sessions> SessionList { get; set; }
 }

15. Sıra geldi Controllerımızı oluşturmaya, Controllers klasörüne sağ tıklayıp Add->Controller’ı seçin ve aşağıdaki resimde görüldüğü gibi gerekli ayarlamaları gerçekleştirin.

Adsız3

16. Bu aşamada Create(Sessions sessions) POST methodunda bir değişiklik yapmaya gerek olmaktadır. Bunun yerine Create GET methodu üzerinde aşağıdaki değişikliği gerçekleştiriniz.


public ActionResult Create()
{
Sessions sessions = new Sessions();
OpenTokSDK opentok = new OpenTokSDK();
string sessionId = opentok.CreateSession(Request.ServerVariables["REMOTE_ADDR");
string token = opentok.GenerateToken(sessionId);

sessions.SessionName = sessionId;
sessions.SessionToken = token;

db.SessionList.Add(sessions);
db.SaveChanges();

return View(sessions);
}

17. Controllerımızı’da ayarladıktan sonra, Şimdi View’larımız üzerindeki değişikliklerimizide yaparak projemizi bitirelim.

Bu aşamada Views->Sessions->Create.cshtml view’ını açalım.
Kod aşağıdaki gibidir.

@model OpenTokTest.Models.Sessions

@{
    ViewBag.Title = "Create";
}
<script src="http://static.opentok.com/v1.1/js/TB.min.js" type="text/javascript" charset="utf-8"></script>
<script type="text/javascript" charset="utf-8">
 var apiKey = "23153492"; // Replace with your API key. See https://dashboard.tokbox.com/projects
 var sessionId = '@Ajax.JavaScriptStringEncode(Model.SessionName)'; // Replace with your own session ID. See https://dashboard.tokbox.com/projects
 var token = "@Ajax.JavaScriptStringEncode(Model.SessionToken)"; // Replace with a generated token. See https://dashboard.tokbox.com/projects

var session;
 var publisher;
 var subscribers = {};
 var VIDEO_WIDTH = 320;
 var VIDEO_HEIGHT = 240;

TB.addEventListener("exception", exceptionHandler);

// Un-comment the following to set automatic logging:
 // TB.setLogLevel(TB.DEBUG);

if (TB.checkSystemRequirements() != TB.HAS_REQUIREMENTS) {
 alert("You don't have the minimum requirements to run this application."
 + "Please upgrade to the latest version of Flash.");
 } else {
 session = TB.initSession(sessionId); // Initialize session

// Add event listeners to the session
 session.addEventListener('sessionConnected', sessionConnectedHandler);
 session.addEventListener('sessionDisconnected', sessionDisconnectedHandler);
 session.addEventListener('connectionCreated', connectionCreatedHandler);
 session.addEventListener('connectionDestroyed', connectionDestroyedHandler);
 session.addEventListener('streamCreated', streamCreatedHandler);
 session.addEventListener('streamDestroyed', streamDestroyedHandler);
 }
 function connect() {
 session.connect(apiKey, token);
 }

function disconnect() {
 session.disconnect();
 hide('disconnectLink');

 }
 function startPublishing() {
 if (!publisher) {
 var parentDiv = document.getElementById("myCamera");
 var publisherDiv = document.createElement('div'); // Create a div for the publisher to replace
 publisherDiv.setAttribute('id', 'opentok_publisher');
 parentDiv.appendChild(publisherDiv);
 var publisherProps = { width: VIDEO_WIDTH, height: VIDEO_HEIGHT };
 publisher = TB.initPublisher(apiKey, publisherDiv.id, publisherProps); // Pass the replacement div id and properties
 session.publish(publisher);
 show('unpublishLink');
 hide('publishLink');
 }
 }

function stopPublishing() {
 if (publisher) {
 session.unpublish(publisher);
 }
 publisher = null;

show('publishLink');
 hide('unpublishLink');
 }

function sessionConnectedHandler(event) {
 // Subscribe to all streams currently in the Session
 for (var i = 0; i < event.streams.length; i++) {
 addStream(event.streams[i]);
 }
 show('disconnectLink');
 startPublishing();
 hide('connectLink');
 }

function streamCreatedHandler(event) {
 // Subscribe to the newly created streams
 for (var i = 0; i < event.streams.length; i++) {
 addStream(event.streams[i]);
 }
 }

function streamDestroyedHandler(event) {
 // This signals that a stream was destroyed. Any Subscribers will automatically be removed.
 // This default behaviour can be prevented using event.preventDefault()
 }

function sessionDisconnectedHandler(event) {
 // This signals that the user was disconnected from the Session. Any subscribers and publishers
 // will automatically be removed. This default behaviour can be prevented using event.preventDefault()
 publisher = null;

show('connectLink');
 stopPublishing();
 }

function connectionDestroyedHandler(event) {
 // This signals that connections were destroyed
 }

function connectionCreatedHandler(event) {
 // This signals new connections have been created.
 }

/*
 If you un-comment the call to TB.setLogLevel(), above, OpenTok automatically displays exception event messages.
 */
 function exceptionHandler(event) {
 alert("Exception: " + event.code + "::" + event.message);
 }
 function addStream(stream) {
 // Check if this is the stream that I am publishing, and if so do not publish.
 if (stream.connection.connectionId == session.connection.connectionId) {
 return;
 }
 var subscriberDiv = document.createElement('div'); // Create a div for the subscriber to replace
 subscriberDiv.setAttribute('id', stream.streamId); // Give the replacement div the id of the stream as its id.
 document.getElementById("subscribers").appendChild(subscriberDiv);
 var subscriberProps = { width: VIDEO_WIDTH, height: VIDEO_HEIGHT };
 subscribers[stream.streamId] = session.subscribe(stream, subscriberDiv.id, subscriberProps);
 }

function show(id) {
 document.getElementById(id).style.display = 'block';
 }

function hide(id) {
 document.getElementById(id).style.display = 'none';
 }
</script>
<h2>Create</h2>

<div>
    <input type="button" value="Connect" id="connectLink" onclick="javascript: connect()" />
    <input type="button" value="Leave" id="disconnectLink" onclick="javascript: disconnect()" />
</div>
<div id="myCamera" class="publisherContainer"></div>
<div id="subscribers"></div>
<script type="text/javascript" charset="utf-8">
    show('connectLink');
</script>
<div>
    @Html.ActionLink("Back to List", "Index")
</div>

@section Scripts {
    @Scripts.Render("~/bundles/jqueryval")
}

Kodda kullanılan JavaScript OpenTok API Basic Tutorial’dan alınmıştır.
18. Şu ana kadar yeni bir stream yayına başlamayı gerçekleştirdik. Sıra geldi yayında olan bir stream’e katılmaya.
Views->Sessions->Details.cshtml view’ını açarak aşağıdaki düzenlemeyi yapınız. Burdaki JavaScript Koduda yine OpenTok API Basic Tutorial’dan alınmıştır.

@model OpenTokTest.Models.Sessions

@{
    ViewBag.Title = "Details";
}
<script src="http://static.opentok.com/v1.1/js/TB.min.js" type="text/javascript" charset="utf-8"></script>
<script type="text/javascript" charset="utf-8">
 var apiKey = "apiKey";
 var sessionId = '@Ajax.JavaScriptStringEncode(Model.SessionName)';
 var token = '@Ajax.JavaScriptStringEncode(Model.SessionToken)';

var session;
 var publisher;
 var subscriber = {};
 var VIDEO_WIDTH = 320;
 var VIDEO_HEIGHT = 240;

TB.addEventListener("exception", exceptionHandler);

if (TB.checkSystemRequirements() != TB.HAS_REQUIREMENTS) {
 alert("You don't have the minimum requirements to run this application."
 + "Please upgrade to the latest version of Flash.");
 }
 else {
 session = TB.initSession(sessionId);
 session.addEventListener("sessionConnected", sessionConnectedHandler);
 session.addEventListener("sessionDisconnected", sessionDisconnectedHandler);
 session.addEventListener("connectionCreated", connectionCreatedHandler);
 session.addEventListener("connectionDestroyed", connectionDestroyedHandler);
 session.addEventListener('streamCreated', streamCreatedHandler);
 session.addEventListener('streamDestroyed', streamDestroyedHandler);
 }
 function connect() {
 session.connect(apiKey, token);
 }
 function disconnect() {
 session.disconnect();
 hide("disconnectLink");
 }

function sessionConnectedHandler(event) {
 for (var i = 0; i < event.streams.length; i++) {
 addStream(event.streams[i]);
 }
 show("disconnectLink");
 hide("connectLink");
 }
 function streamCreatedHandler(event) {
 // Subscribe to the newly created streams
 for (var i = 0; i < event.streams.length; i++) {
 addStream(event.streams[i]);
 }
 }
 function streamDestroyedHandler(event) {
 // This signals that a stream was destroyed. Any Subscribers will automatically be removed.
 // This default behaviour can be prevented using event.preventDefault()
 }
 function sessionDisconnectedHandler(event) {
 // This signals that the user was disconnected from the Session. Any subscribers and publishers
 // will automatically be removed. This default behaviour can be prevented using event.preventDefault()
 publisher = null;

show('connectLink');
 hide('disconnectLink');
 hide('publishLink');
 hide('unpublishLink');
 }
 function connectionDestroyedHandler(event) {
 // This signals that connections were destroyed
 }

function connectionCreatedHandler(event) {
 // This signals new connections have been created.
 }

/*
 If you un-comment the call to TB.setLogLevel(), above, OpenTok automatically displays exception event messages.
 */
 function exceptionHandler(event) {
 alert("Exception: " + event.code + "::" + event.message);
 }
 function addStream(stream) {
 // Check if this is the stream that I am publishing, and if so do not publish.
 if (stream.connection.connectionId == session.connection.connectionId) {
 return;
 }
 var subscriberDiv = document.createElement('div'); // Create a div for the subscriber to replace
 subscriberDiv.setAttribute('id', stream.streamId); // Give the replacement div the id of the stream as its id.
 document.getElementById("subscribers").appendChild(subscriberDiv);
 var subscriberProps = { width: VIDEO_WIDTH, height: VIDEO_HEIGHT };
 subscribers[stream.streamId] = session.subscribe(stream, subscriberDiv.id, subscriberProps);
 }

function show(id) {
 document.getElementById(id).style.display = 'block';
 }

function hide(id) {
 document.getElementById(id).style.display = 'none';
 }
</script>
<h2>Details</h2>

<fieldset>
    <legend>Sessions</legend>

    <div class="display-label">
        @Html.DisplayNameFor(model => model.SessionName)
    </div>
    <div class="display-field">
        @Html.DisplayFor(model => model.SessionName)
    </div>
</fieldset>
<p>
    <input type="button" value="Connect" id="connectLink" onclick="javascript:connect()" />
    <input type="button" value="Leave" id="disconnectLink" onclick="javascript: disconnect()" />
</p>
<div id="myCamera" class="publisherContainer"></div>
<div id="subscribers"></div>
<script type="text/javascript" charset="utf-8">
    show('connectLink');
</script>

19. Projemizi şu an tamamlamış bulunmaktayız. Test etmek için F5’e basarak tarayıcınızda projeyi çalıştırınız ve adres satırında http://localhost:port_No/OpenTokAPITest/Sessions gerekli düzenlemeyi yaparak test işlemini gerçekleştiriniz.

Bu projeyi hazırlarken herhangi bir kodlama tekniği kullanmadım. Gereksiz kod olabilir, isteyenler bunu dahada geliştirip kullanabilirler.

Teşekkürler,

Yukarıdaki kodun bitmiş halini burdan indirebilirsiniz.

logo_sky