Tuesday, April 30, 2013

Android MapActivity cannot be resolved

While I was working in a Android Map based application, I came across that MapActivty couldn't be resolved. Since I was upgraded my SDK Tools & SDK Platform Tools to the very latest versions, I was unable to set the target of my app to Google API [desired version] as mentioned in many tutorials. Finnaly I was able to fix the issue by manually setting the Android Build Target of my project to Google API(Platform 3.1, API Level 12)

Eclipse -> Select the project -> Properties -> Android -> Target Name -> tick the desired Google API level

Accessing WCF Service via Android

Recent past as an R&D Project I was working on a prototype basis Shopping cart application (assuming that the end-users are always in a connected environment-WiFi/3G) which has no local database so that it had to interact with WCF Service for data-manipulation.

WCF Service, data handling section was developed using Entity Framework(Code First approach). There were several modules like Item, Category, Order etc. Among those I picked Item module for further explanation.

WCF Service

Entity
public class Item{

        public string Id { get; set; }

        public string Name { get; set; }

        public string Url { get; set; }

        public string CategoryId { get; set; }

        public virtual Category Category { get; set; }

        public int InStock { get; set; }

        public decimal Price { get; set; }

 }

Mapping
public class ItemMap : EntityTypeConfiguration<Item>
{
        public ItemMap()
        {
            ToTable("tbl_Item");
            HasKey(item => item.Id);

            HasRequired(item => item.Category)
                .WithMany()
                .HasForeignKey(item => new { item.CategoryId });
        }   
}

Repository
public class ItemRepo
{
        protected IDbSet<Item> ItemSet;
        protected DataContext Context;

        public ItemRepo(DataContext dataContext)
        {
            Context = dataContext;
            ItemSet = dataContext.Set<Item>();
        }

         public List<Item> GetItems(string from, string to)
        {
            ItemSet.Include(item => item.Category);
            IEnumerable<Item> items = (from a in ItemSet
                                       select a).OrderBy(a =>                  a.Id).Skip(Convert.ToInt32(from)).Take(Convert.ToInt32(to));

            return items.ToList();
        }     
}

WCF Service Method
[OperationContract]
[WebGet(ResponseFormat = WebMessageFormat.Json)]
public List<Item> GetItems(string From, string To)
{
       var itemRepo = new ItemRepo(new DataContext());
       return itemRepo.GetItems(From, To);
}

Android-Client side

You have to access the WCF Service with a similar function like below. I have used a third party library called gson-1.7.1(not the latest one), which can be downloaded from the below link.
download google-gson

Item-Mapping [since my mapping properties had the same name with compared to the json result item list, i have not used the SerializedName annotation]

Mapping

public class Item {

private String Id;
private String Name;
private String Url;
private int InStock;
private Integer OrderQty;
private Double Price;

public String getId() {
 return Id;
}
public void setId(String id) {
 Id = id;
}
public String getName() {
 return Name;
}
public void setName(String name) {
 Name = name;
}
public Integer getOrderQty() {
 return OrderQty;
}
public void setOrderQty(int orderQty) {
 OrderQty = orderQty;
}
public int getInStock() {
 return InStock;
}
public void setInStock(int inStock) {
 InStock = inStock;
}
public String getUrl() {
 return Url;
}
public void setUrl(String url) {
 Url = url;
}
public Double getPrice() {
 return Price;
}
public void setPrice(Double price) {
 Price = price;
}
}


WCF Service accessing method

public List<Item> getItems(String from, String to) {

   List<Item> items = null;
   Gson gson = new Gson();

   try {

  String urlWithParam = String.format("http://app.dinotait.com/Items/HTML5Service.svc/GetItems?From=%s&To=%s",from, to);
  
  HttpGet request = new HttpGet(urlWithParam);

request.setHeader("Accept", "application/json");
  request.setHeader("Content-type", "application/json");

DefaultHttpClient httpClient = new DefaultHttpClient();
  HttpResponse response = httpClient.execute(request);

HttpEntity responseEntity = response.getEntity();

// Read response data into buffer
  char[] buffer = new char[(int) responseEntity.getContentLength()];
  InputStream stream = responseEntity.getContent();
  InputStreamReader reader = new InputStreamReader(stream);
  reader.read(buffer);
  stream.close();
 
  Type type = new TypeToken<List<Item>>(){}.getType();

  items = gson.fromJson(new String(buffer), type);

} catch (Exception e) {
e.printStackTrace();
}

   return items;
}


Remember that you have to execute this function within an AsyncTask or similar approach since this is a network operation.




Wednesday, February 20, 2013

Add Unallocated Space to an existing partition (Windows 7 32-bit)

I came across a situation like this while i'm working in my office. My office-pc's(OS: Windows 7 32-bit) hard disk had an unallocated space around 30GB. I didn't want to make use of this space to create another separate partition (already having 3 separate partitions), what I wanted is to extend an existing partition with it. What I did was mentioned in step-by-step below.

Open the command-prompt and type diskpart.exe.
This directs you to diskpart shell window DISKPART>

Then select the volume which you want to extend, in my case it was E drive, so I type 7 enter,
DISKPART>  select volume E

It will show,
"Volume 4 is the selected volume" (in my case, it is the E drive)

Then type and enter,
DISKPART> extend noerr
If all goes well, you will be seen "diskpart successfully extended the volume".

sourcehttp://www.ehow.com/how_6797254_add-unallocated-space-partition-xp.html

Wednesday, January 23, 2013

Multiple images uploading (with file size reduced) + MVC4, JQuery mobile, XMLHttpRequest, HTML5 File Api

I had to work with a project that had the functionality of multiple image files uploading. The specialty of the functionality was it had the ability of uploading larger images with reduced file sizes apart from uploading the original files. I thought of sharing the basic functionality of size reduced files-uploading.

Technologies used : MVC4, JQuery mobile, XMLHttpRequest, HTML5 File Api

MVC4 View

@{
    ViewBag.Title = "File Upload";
}

<div>
    <input type="file" accept="image/*" name="fileToUpload[]" id="fileToUpload" style='visibility: hidden;'
        name="img" onchange="fileSelected();" />
    <input type="button" value="Choose image"  onclick="javascript:document.getElementById('fileToUpload').click();">
    <ul data-role="listview" id="uploadfilelist" data-inset="true" data-split-theme="d"
        data-split-icon="delete">
    </ul>
</div>
<div>
    <ul data-role="listview" data-inset="true">
        <li data-role="fieldcontain">
            <input type="button" onclick="uploadFiles();" value="Upload [max. 5 files]" />
        </li>
    </ul>
</div>

There were several javascript functions I have written to fulfill the requirement. 

  • fileSelected - this function is used to show preview of the selected file. Also I have written some validations such as only image types are allowed, maximum file size is 10MB, no.of files that can be uploaded at once cannot be higher than 5. Remember that your browser should be supported HTML5 File Api.
  • uploadFiles - loop through filequeue and popping up the file and the list-element.
  • resizeAndUpload - this function does the size reducing before uploading. At the moment I have used the MAX Height as 600 and MAX Width as 800. I have use the canvas element and redraw the original image with the max height, width dimensions.  XMLHttpRequest object is used to send the data(canvas element can be converted to base64string with the use of toDataURL("image/jpeg")) to server.

javascript code


<script type="text/javascript">

    var filequeue = new Array();

    function fileSelected() {

        try {

            if (window.File && window.FileReader && window.FileList && window.Blob) {
                
                var selectedfile;

                var files = document.getElementById('fileToUpload').files;
                if (filequeue.length > 4) {
                    alert('Maximum number of allowable file uploads has been exceeded!!');
                } else {

                    selectedfile = files[0];

                    if (!selectedfile.type.match('image.*')) {
                        alert('Only image files are allowed');
                    } else if (selectedfile.size > 10485760) {
                        alert('Maximum file size exceeds');
                    }

                    if (selectedfile.type.match('image.*') && selectedfile.size < 10485760) {

                        var reader = new FileReader();

                        reader.onload = (function(theFile) {
                            return function(e) {

                                var li = document.createElement("li");
                                li.setAttribute("data-icon", "delete");

                                var newlink = document.createElement('a');

                                var img = document.createElement("img");
                                img.setAttribute("src", e.target.result);
                                img.setAttribute("height", "80");
                                img.setAttribute("width", "80");
                                newlink.appendChild(img);

                                var h3 = document.createElement("h3");
                                var h3Text = document.createTextNode(theFile.name);
                                h3.appendChild(h3Text);
                                newlink.appendChild(h3);

                                li.appendChild(newlink);

                                document.getElementById("uploadfilelist").appendChild(li);

                                $("#uploadfilelist").listview("refresh");

                                filequeue.push({ file: theFile, lisetElement: li });

                            };
                        })(selectedfile);

                        reader.readAsDataURL(selectedfile);

                    }

                }
                
            }else {
                alert("html5 file api is not compatible with this browser!");
            }

            $("#fileToUpload").val("");

        } catch (err) {
            alert("Exception " + err);
        }
    }


    function uploadFiles() {

        try {

            if (filequeue != null && filequeue.length != 0) {
                
                while (filequeue.length > 0) {

                    var item = filequeue.pop();
                    var file = item.file;
                    var li = item.lisetElement;
                    resizeAndUpload(file, li);

                }
            }

        } catch (err) {
            alert("Exception " + err);
        }

    }

    function resizeAndUpload(file, li) {

        try {

            if (window.File && window.FileReader && window.FileList && window.Blob) {

                var uploadurl = '@Url.Action("UploadSizeReducedFiles", "FileUpload")';

                var reader = new FileReader();
                reader.onloadend = function(evt) {

                    if (evt.target.readyState == FileReader.DONE) {

                        var tempImg = new Image();

                        tempImg.onload = function() {

                            var MAX_WIDTH = 800;
                            var MAX_HEIGHT = 600;
                            
                            var tempWidth = tempImg.width;
                            var tempHeight = tempImg.height;

                            if (tempWidth > tempHeight) {
                                if (tempWidth > MAX_WIDTH) {
                                    tempHeight *= MAX_WIDTH / tempWidth;
                                    tempWidth = MAX_WIDTH;
                                }
                            } else {
                                if (tempHeight > MAX_HEIGHT) {
                                    tempWidth *= MAX_HEIGHT / tempHeight;
                                    tempHeight = MAX_HEIGHT;
                                }
                            }

                            var canvas = document.createElement('canvas');
                            canvas.setAttribute("height", tempHeight);
                            canvas.setAttribute("width", tempWidth);
                            var context = canvas.getContext("2d");
                            context.drawImage(tempImg, 0, 0, tempWidth, tempHeight);

                            var xhr = new XMLHttpRequest();
                            xhr.open("POST", uploadurl);
                            xhr.setRequestHeader("Content-type", "application/json; charset=utf-8");
                            xhr.setRequestHeader("X-File-Name", file.name);
                            var data = 'image=' + canvas.toDataURL("image/jpeg");
                            xhr.send(data);

                            xhr.onreadystatechange = function() {

                                var containtext;

                                if (xhr.readyState != 4) {
                                    return;
                                }

                                else if (xhr.readyState == 4) {

                                    if (xhr.status == 500) {

                                        containtext = $(li).find("h3").text();
                                        $(li).find("h3").text(containtext + " upload error");
                                        $(li).find("h3").css("color", "#FF0000");

                                    }
                                    else if (xhr.status == 200) {

                                        containtext = $(li).find("h3").text();
                                        $(li).find("h3").text(containtext + " upload complete");

                                    }

                                }

                            };

                        };
                        tempImg.src = reader.result;

                    };

                };
                reader.readAsDataURL(file);

            } else {
                alert("html5 file api is not compatible with this browser!");
            }

        }
        catch(err) {
            alert("Exception " + err);
        }
    }

</script>

FileUpload Controller

This method handles the file saving to the server-side folder which is Uploads in my scenario, the status of the uploaded file will be displayed in the file uploading list.

[AcceptVerbs(HttpVerbs.Post)]
[OutputCache(NoStore = true, Duration = 0, VaryByParam = "*")]
public JsonResult UploadSizeReducedFiles()
{
    string fileName = null;
    string uploadedFilePath = null;

    try
    {

        fileName = Request.Headers["X-File-Name"];

        var directoryPath = Server.MapPath("~/Uploads/");

        if (!Directory.Exists(directoryPath))
        {
            Directory.CreateDirectory(directoryPath);
        }
                
        var stream = new StreamReader(Request.InputStream);
        var image = stream.ReadToEnd();

        image = image.Substring("image=data:image/jpeg;base64,".Length);
        var buffer = Convert.FromBase64String(image);

        uploadedFilePath = string.Format("{0}{1}", directoryPath, fileName);

        System.IO.File.WriteAllBytes(uploadedFilePath, buffer);

        return Json(fileName + " completed", JsonRequestBehavior.AllowGet);
    }
    catch (Exception e)
    {
        if (System.IO.File.Exists(uploadedFilePath))
        {
            if (uploadedFilePath != null) System.IO.File.Delete(uploadedFilePath);
        }

        Response.StatusCode = 500;
        return Json(fileName + " fail", JsonRequestBehavior.AllowGet);
    }
}

For functions like size reduce file uploading along with original file uploading, remove selected files before uploading, file uploading progress indicator please contact me via email.


Monday, January 7, 2013

Finding the location of a running process under Windows XP

I came across find in a location of a running process under Windows XP. It was not just as easy as Windows 7. Because in Windows 7, we can use TaskManager -> Processes -> Select a process & right click -> Open File Location to find the exact place of the running process.

But in Windows XP, you can achieve it by using command prompt and type one of the following command

Information about all Processes
WMIC /OUTPUT:C:\ProcessList.txt PROCESS get Caption, Commandline, Processid

Information about one process
WMIC /OUTPUT:"C:\ProcessList.txt" process where "caption='EMTC-Demo.exe'" get Caption,Commandline,Processid

hint: EMTC-Demo.exe is the process name

Sunday, December 23, 2012

Microsoft JScript runtime error: '$' is undefined in MVC4 Mobile Web Application

I came across this problem while I was developing a mobile web application in MVC4. I think most of you all have faced this issue and found a solution as well. But I thought it was worth to share this, becuase this did the trick for me.
In my MVC4 web application , I had my _Layout.cshtml page like this.

<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="utf-8" />
        <title>@ViewBag.Title</title>
        <meta name="viewport" content="width=device-width" />
        <link href="~/favicon.ico" rel="shortcut icon" type="image/x-icon" />
        @Styles.Render("~/Content/mobileCss", "~/Content/css")
        @Scripts.Render("~/bundles/modernizr")
    </head>
    <body>
        <div data-role="page" data-theme="b">
            <div data-role="header">
                @if (IsSectionDefined("Header")) {
                    @RenderSection("Header")
                } else {
                    <h1>@ViewBag.Title</h1>
                    @Html.Partial("_LoginPartial")
                }
            </div>
            <div data-role="content">
                @RenderBody()
            </div>
        </div>

        @Scripts.Render("~/bundles/jquery", "~/bundles/jquerymobile")
        @RenderSection("scripts", required: false)
    </body>
</html>

But inorder to resolve the error, I had to modify the page like below.

<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="utf-8" />
        <title>@ViewBag.Title</title>
        <meta name="viewport" content="width=device-width" />
        <link href="~/favicon.ico" rel="shortcut icon" type="image/x-icon" />
        @Styles.Render("~/Content/mobileCss", "~/Content/css")
        @Scripts.Render("~/bundles/modernizr")
        @Scripts.Render("~/bundles/jquery", "~/bundles/jquerymobile")
     
    </head>
    <body>
        <div data-role="page" data-theme="b">
            <div data-role="header">
                @if (IsSectionDefined("Header")) {
                    @RenderSection("Header")
                } else {
                    <h1>@ViewBag.Title</h1>
                    @Html.Partial("_LoginPartial")
                }
            </div>
            <div data-role="content">
                @RenderBody()
            </div>
        </div>
     
        @RenderSection("scripts", required: false)
    </body>
</html>

Note that I changed the place of JQuery script line from section <body> to <head>.
source : http://forums.asp.net/t/1835597.aspx/1

Monday, December 3, 2012

Windows Phone 7 Photo Upload

Recently I have developed a native Windows Phone 7 program to upload images to remote server.

MainPage.xaml

<!--ContentPanel - place additional content here-->
<Grid x:Name="ContentPanel" Grid.Row="1" Margin="12,0,12,0">

            <ListBox Height="517" Margin="0,6,0,0" Name="listimge" VerticalAlignment="Top" Width="450">

                <ListBox.ItemTemplate>
                    <DataTemplate>
                        <StackPanel Orientation="Horizontal">
                            <CheckBox Name="chk" /><Image Source="{Binding ImageFile}" Width="100" Height="100"/>
                            
                        </StackPanel>
                    </DataTemplate>
                </ListBox.ItemTemplate>
            </ListBox>
            <Button Content="Upload" Height="72" HorizontalAlignment="Left" Margin="150,529,0,0" Name="uploadButton" 
            VerticalAlignment="Top" Width="160" Click="UploadClick" />

</Grid>


MainPage.xaml.cs

The below method is used to load image files from the Picture Gallery to the ListBox.
private MediaLibrary MyMediaLibrary { get; set; }

private void LoadImageGallery()
{
            MyMediaLibrary = new MediaLibrary();
            PictureCollection pictures = MyMediaLibrary.Pictures;
            foreach (Picture picture in pictures)
            {
                var image = new BitmapImage();
                image.SetSource(picture.GetImage());
                var mediaImage = new MediaImage {ImageFile = image};
                listimge.Items.Add(mediaImage);
            }
}

This method is used to upload the selected images(iterating through the ListBox to find the selected index) to the remote server.
private void UploadClick(object sender, RoutedEventArgs e)
{
            for (int i = 0; i < listimge.Items.Count; i++)
            {
                if (listimge.ItemContainerGenerator != null)
                {
                    var item = listimge.ItemContainerGenerator.ContainerFromIndex(i) as ListBoxItem;
                    var tagregCheckBox = FindCheckBox<CheckBox>(item);
                    if (tagregCheckBox.IsChecked == true)
                    {
                        UploadImage(i);
                        tagregCheckBox.IsChecked = false;
                    }
                }
            }
}

Helper function which is used to identify the checked Checkboxses in the ListBox.
private T FindCheckBox<T>(DependencyObject parentElement) where T : DependencyObject
{
            int count = VisualTreeHelper.GetChildrenCount(parentElement);
            if (count == 0)
                return null;

            for (int i = 0; i < count; i++)

            {
                DependencyObject child = VisualTreeHelper.GetChild(parentElement, i);

                if (child != null && child is T)

                {
                    return (T) child;
                }
                var result = FindCheckBox<T>(child);
                if (result != null)
                    return result;
            }
            return null;
}

This method is used to find the image from image gallery, get the stream of the identified image and send it to the remote server.
private void UploadImage(int selectedIndex)
{
            const int BLOCK_SIZE = 4096;

            var uri = new Uri("http://10.20.10.71/MVCFile/File", UriKind.Absolute);


            var webClient = new WebClient();

            webClient.AllowReadStreamBuffering = true;
            webClient.AllowWriteStreamBuffering = true;

            Stream selectedImageStream = MyMediaLibrary.Pictures[selectedIndex].GetImage();


            webClient.OpenWriteCompleted += (s, args) =>

                                                {
                                                    using (var binaryReader = new BinaryReader(selectedImageStream ))
                                                    {
                                                        using (var binaryWriter = new BinaryWriter(args.Result))
                                                        {
                                                            long count = 0;
                                                            long fileSize = selectedImageStream .Length;
                                                            var bytes = new byte[BLOCK_SIZE];
                                                            do
                                                            {
                                                                bytes = binaryReader.ReadBytes(BLOCK_SIZE);
                                                                count += bytes.Length;
                                                                binaryWriter.Write(bytes);
                                                            } while (count < fileSize);
                                                        }
                                                    }
                                                };

            webClient.WriteStreamClosed += (s, args) => { MessageBox.Show("Send Complete"); };


            webClient.OpenWriteAsync(uri, "POST");

}

Finally add the 'LoadImageGallery' method to the constructor of MainPage.
// Constructor
public MainPage()
{
            InitializeComponent();
            LoadImageGallery();
}


Server side File Uploading Controller
public class FileController : Controller
{
       public ActionResult Index()
      {
            string filename = Server.MapPath(String.Format("{0}.jpg", "YourFileName"));

            try

            {
                using (var fs = new FileStream(filename, FileMode.Create))
                {
                    using (var bw = new BinaryWriter(fs))
                    {
                        using (var br = new BinaryReader(Request.InputStream))
                        {
                            long bCount = 0;
                            long fileSize = br.BaseStream.Length;
                            const int BLOCK_SIZE = 4096;
                            byte[] bytes = new byte[BLOCK_SIZE];
                            do
                            {
                                bytes = br.ReadBytes(BLOCK_SIZE);
                                bCount += bytes.Length;
                                bw.Write(bytes);
                            } while (bCount < fileSize);
                        }
                    }
                }

                return Json(new { Result = "Upload Complete" }, JsonRequestBehavior.AllowGet);

            }
            catch (Exception ex)
            {
                return Json(new { Result = "Upload Error", Message = ex.Message }, JsonRequestBehavior.AllowGet);
            }
      }
}