C# MVC Read Blog Items into an array

Every now and then you would want to enrich your MVC application by displaying a live feed of articles from a blog.
Here is how to do it!

[HttpGet]
public string GetInfo()
{
ArrayList _socialItemsArray = new ArrayList(50);
var i = 0;
var reader2 = System.Xml.XmlReader.Create(“http://myblogurl/feed/”);
var feed2 = System.ServiceModel.Syndication.SyndicationFeed.Load(reader2);
reader2.Close();
foreach (System.ServiceModel.Syndication.SyndicationItem album in feed2.Items)
{

i++;
if (i > 10) { break; }
SocialItem x = new SocialItem();
x.account = “WordPress”;
x.Link = album.Links.First().Uri.ToString();
x.created_at = DateTime.Parse(album.PublishDate.ToString(“g”));

if (album.Title.Text.Length > 90)
{
x.UserDisplayName = album.Title.Text.Substring(0, 87) + “…”;
}
else
{
x.UserDisplayName = album.Title.Text;
}

string postSummary = album.Summary.Text;

if (postSummary.Length >135)
{
postSummary = postSummary.Substring(0, 135);
int lastSpace = postSummary.LastIndexOf(” “);

if (lastSpace != -1)
{
postSummary = postSummary.Substring(0, lastSpace) + “…”;
}
else
{
postSummary = postSummary + “…”;
}
}
x.Content = postSummary;

_socialItemsArray.Add(x);
}

}

If you wish to display the information, just look in the _socialItemsArray and traverse it with a for, foreach or while statement.

Advertisements

setInterval not working in iOS 8 – Home Screen Apps Lose Timing Functions After Lock/Wake

ios_8_logo

If your application is being used as a homescreen web application, you’ll find yourself in a sorry state. Of course, any web app can be converted into a home screen app by the user, so I guess technically this affects anyone making a remote web application. This bug is easily reproduced by simply calling setTimeout(callback, 1) or requestAnimationFrame(callback) via some button or event. When you first open your application, you’ll notice all timing functions are working fine. However if you lock your phone and then unlock to return to your application, you’ll see none of the timing functions can call callbacks anymore. They are simply broken at a native level. There is no reset, no bringing your application back to life, it’s a kill it and restart situation.

These timing functions are crucial to pretty much every other JavaScript framework/library ever made. Definitely head over to Apple as soon as you can, and let them know that you would like to have all of your JavaScript functions, all the time.

Radar Bug Report: http://www.openradar.me/radar?id=5895945212395520

 

Alternative to setInterval and setTimeout

JavaScript’s setTimeout and setInterval are evil and not precise…

  1. both have a delay of various milliseconds http://www.andrewduthie.com/post/a-self-correcting-setinterval-alternative/
  2. both are very resource intensive as they execute several times every second.

A new alternative is requestAnimationFrame. it’s less resource=intensive, does not slow down other stuff and it is disabled on page blur.

This makes it the perfect substitute for a modern setTimeout and setInterval.

So I wrote this functions:

Description

This functions use requestAnimationframe to check if the time is passed based on the elapsed Time calculated from Date.now. The time passed is more precise than the native functions and theoretically less resource intensive. Another advantage/disadvantage(depends) is that the functions are not executed on page blur.

Good for: animations, visual effects

Bad for: timers, clock

RafTimeout

window.rtimeOut=function(callback,delay){
 var dateNow=Date.now,
     requestAnimation=window.requestAnimationFrame,
     start=dateNow(),
     stop,
     timeoutFunc=function(){
      dateNow()-start<delay?stop||requestAnimation(timeoutFunc):callback()
     };
 requestAnimation(timeoutFunc);
 return{
  clear:function(){stop=1}
 }
}

RafInterval

window.rInterval=function(callback,delay){
 var dateNow=Date.now,
     requestAnimation=window.requestAnimationFrame,
     start=dateNow(),
     stop,
     intervalFunc=function(){
      dateNow()-start<delay||(start+=delay,callback());
      stop||requestAnimation(intervalFunc)
     }
 requestAnimation(intervalFunc);
 return{
  clear:function(){stop=1}
 }
}

Usage

var interval1,timeout1;
window.onload=function(){
 interval1=window.rInterval(function(){console.log('interval1')},2000);
 timeout1=window.rtimeOut(function(){console.log('timeout1')},5000);
}

/* to clear
interval1.clear();
timeout1.clear();
*/

Demo

http://jsfiddle.net/wZ9Z6/

Are photoshop-like blend modes possible in HTML5?

If you’re a user of our design applications such as Photoshop and Illustrator, you know how you can create very cool effects with blend modes. An Amazon search returns many books and a Google search on ‘photoshop blending tutorial’ returns more than 200,000 results. This points to a very widely known and used feature.

Adobe: http://blogs.adobe.com/webplatform/2012/04/04/bringing-blending-to-the-web/

Capture

To be able to blend to images together like Photoshop does, we will need to use the HTML5 canvas feature. The images are loaded dynamically using Javascript.

The easy way to blend two images together can be summarized into

// Might be an 'offscreen' canvas
var over  = someCanvas.getContext('2d');
var under = anotherCanvas.getContext('2d');

over.blendOnto( under, 'screen', {destX:30,destY:15} );

The full example is featured below:

The HTML

Blending mode
Opacity
</div> <canvas id="canvas2" width="300" height="300"></canvas> </section> <section class="result"> <canvas id="result" width="300" height="300"></canvas> </section> </div>

The Javascript Code

At first we define the blending modes:

var blendingModes = {
	normal: function(a, b) {
		return a;
	},

	lighten: function(a, b) {
		return (b > a) ? b : a;
	},

	darken: function(a, b) {
		return (b > a) ? a : b;
	},

	multiply: function(a, b) {
		return (a * b) / 255;
	},

	average: function(a, b) {
		return (a + b) / 2;
	},

	add: function(a, b) {
		return Math.min(255, a + b);
	},

	substract: function(a, b) {
		return (a + b < 255) ? 0 : a + b - 255; 	}, 	difference: function(a, b) { 		return Math.abs(a - b); 	}, 	negation: function(a, b) { 		return 255 - Math.abs(255 - a - b); 	}, 	screen: function(a, b) { 		return 255 - (((255 - a) * (255 - b)) >> 8);
	},

	exclusion: function(a, b) {
		return a + b - 2 * a * b / 255;
	},

	overlay: function(a, b) {
		return b < 128
			? (2 * a * b / 255)
			: (255 - 2 * (255 - a) * (255 - b) / 255);
	},

	softLight: function(a, b) {
		return b < 128 			? (2 * ((a >> 1) + 64)) * (b / 255)
			: 255 - (2 * (255 - (( a >> 1) + 64)) * (255 - b) / 255);
	},

	hardLight: function(a, b) {
		return blendingModes.overlay(b, a);
	},

	colorDodge: function(a, b) {
		return b == 255 ? b : Math.min(255, ((a << 8 ) / (255 - b)));
	},

	colorBurn: function(a, b) {
		return b == 0 ? b : Math.max(0, (255 - ((255 - a) << 8 ) / b));
	},

	linearDodge: function(a, b) {
		return blendingModes.add(a, b);
	},

	linearBurn: function(a, b) {
		return blendingModes.substract(a, b);
	},

	linearLight: function(a, b) {
		return b < 128
			? blendingModes.linearBurn(a, 2 * b)
			: blendingModes.linearDodge(a, (2 * (b - 128)));
	},

	vividLight: function(a, b) {
		return b < 128
			? blendingModes.colorBurn(a, 2 * b)
			: blendingModes.colorDodge(a, (2 * (b - 128)));
	},

	pinLight: function(a, b) {
		return b < 128
			? blendingModes.darken(a, 2 * b)
			: blendingModes.lighten(a, (2 * (b - 128)));
	},

	hardMix: function(a, b) {
		return blendingModes.vividLight(a, b) < 128 ? 0 : 255;
	},

	reflect: function(a, b) {
		return b == 255 ? b : Math.min(255, (a * a / (255 - b)));
	},

	glow: function(a, b) {
		return blendingModes.reflect(b, a);
	},

	phoenix: function(a, b) {
		return Math.min(a, b) - Math.max(a, b) + 255;
	}
};

The Blending Code

/** @type CanvasRenderingContext2D */
var ctx1 = null;

/** @type CanvasRenderingContext2D */
var ctx2 = null;

/** @type CanvasRenderingContext2D */
var ctx3 = null;

/** Current blending mode */
var mode = 'normal';

/** Current blending opacity */
var alpha = 1;

var totalImages = 2;
var img1 = new Image;
var img2 = new Image;

img1.onload = img2.onload = imageReady;

function imageReady() {
	if (--totalImages == 0) {
		setupScene();
	}
}

function setupScene() {
	ctx1 = document.getElementById('canvas1').getContext('2d');
	ctx2 = document.getElementById('canvas2').getContext('2d');
	ctx3 = document.getElementById('result').getContext('2d');

	drawImage(img1, ctx1);
	drawImage(img2, ctx2);
	drawImage(img1, ctx3);
}

/**
 * Draw image on specified canvas context
 * @param {Image} img
 * @param {CanvasRenderingContext2D} ctx
 */
function drawImage(img, ctx) {
	ctx.canvas.width = img.width;
	ctx.canvas.height = img.height;
	ctx.drawImage(img, 0, 0);
	updateScene();
}

function updateScene() {
	// create rect for smallest image
	var width =  Math.min(ctx1.canvas.width, ctx2.canvas.width);
	var height = Math.min(ctx1.canvas.height, ctx2.canvas.height);

	var imageData1 = ctx1.getImageData(0, 0, width, height);
	var imageData2 = ctx2.getImageData(0, 0, width, height);

	/** @type Array */
	var pixels1 = imageData1.data;
	/** @type Array */
	var pixels2 = imageData2.data;

	var r, g, b, oR, oG, oB, alpha1 = 1 - alpha;

	var blendingMode = blendingModes[mode];

	// blend images
	for (var i = 0, il = pixels1.length; i < il; i += 4) {
		oR = pixels1[i];
		oG = pixels1[i + 1];
		oB = pixels1[i + 2];

		// calculate blended color
		r = blendingMode(pixels2[i], oR);
		g = blendingMode(pixels2[i + 1], oG);
		b = blendingMode(pixels2[i + 2], oB);

		// alpha compositing
		pixels1[i] =     r * alpha + oR * alpha1;
		pixels1[i + 1] = g * alpha + oG * alpha1;
		pixels1[i + 2] = b * alpha + oB * alpha1;
	}

	ctx3.putImageData(imageData1, 0, 0);
}

/**
 * @param {String} name
 */
function humanizeName(name) {
	return name.charAt(0).toUpperCase() + name.substring(1).replace(/[A-Z]/g, function(s) {
		return ' ' + s.toLowerCase();
	});
}

$(function() {
	// setup page:

	// fill blending mode select box
	var options = [];
	for (var name in blendingModes) if (blendingModes.hasOwnProperty(name)) {
		options.push('' + humanizeName(name) + '');
	}

	$('select[name=blending]').html(options.join('')).change(function() {
		mode = $(this).val();
		if (!totalImages)
			updateScene();
	});

	$('input[name=opacity]').bind('change keyup keypress', function() {
		var value = parseInt($(this).val(), 10);
		if ($(this).data('prev-value') != value) {
			$(this).data('prev-value', value);
			alpha = Math.min(1, Math.max(0, value / 100));

			if (!totalImages)
				updateScene();
		}
	}).val(Math.floor(alpha * 100));

	// load images
	img1.src = 'image1.jpg';
	img2.src = 'image2.jpg';
});

The CSS

body {
			padding: 40px 10px;
			font-family: arial, sans-serif;
			font-size: 12px;
		}

		.blending-demo {
			margin-top: 5em;
			white-space: nowrap;
		}

		section {
			position: relative;
			display: inline-block;
		}

		section:after {
			font-weight: bold;
			font-size: 60px;
			position:absolute;
			top: 50%;
			margin-left: 0.15em;
			left: 100%;
			margin-top: -0.6em;
			line-height: 1.2;
		}

		.image1, .image2 {
			margin-right: 4em;
		}

		.image1:after {
			content: '+';
		}

		.image2:after {
			content: '=';
		}

		.controls {
			position: absolute;
			bottom: 100%;
			padding-bottom: 1em;
		}

		select[name=blending] {
			margin-bottom: 1em;
		}

		label {
			display: inline-block;
			line-height: 1.5;
			vertical-align: middle;
			margin-right: 1em;
			width: 7em;
		}

		input[name=opacity] {
			vertical-align: middle;
		}

The Result

http://media.chikuyonok.ru/canvas-blending/

How to execute long running queries in the background using vb.net

Data-ProcessingSometimes the users to your website will have to wait for an operation to be completed. Sometimes, the wait time is minor – a few seconds at most, sometimes though, this can take a lot longer – spanning from 5-10 minutes to a few hours.

You can optimize your queries to be as efficient as you would like them, but when dealing with a lot of data, this time cannot be reduced significantly.

We have written a few functions to help you with the process.

First, you will need to create a new class that will handle all long running processes:

Imports Microsoft.VisualBasic

Public Class LongProcesses

    Public Sub MatchAllDocuments(params As Object)
        Dim params_local() As Object = CType(params, Object())
        Dim pr As New ProcessFile
        Dim d As New DataLayer
        Dim dtStart As DateTime = Now
        Dim clName As String = d.GetClientName(params_local(0).ToString)
        pr.WriteToLog("Matching all Documents for client " + clName, params_local(0).ToString, params_local(1).ToString)
        Dim strerror As String = d.MatchAllDocuments(Integer.Parse(params_local(0).ToString), params_local(1).ToString)

        Dim ts As TimeSpan = Now.Subtract(dtStart)
        If strerror = "" Then
            Dim strMsg As String = "Dear Administrator,<br /><br />Matching has been completed for client <strong>" + clName
            strMsg += "</strong>.<br />Time required to complete this operation: " + ts.Minutes.ToString() + "min " + ts.Seconds.ToString + "s"
            strMsg += "<br /><br />Thank you,<br />Web Team"
            SendEmailC.SendEmail("support@carra-lucia-ltd.co.uk", "Matching Complete for Client " + clName, strMsg)
        Else
            Dim strMsg As String = "Dear Administrator,<br /><br />Matching could not be completed for client <strong>" + clName
            strMsg += "</strong>.<br />Time required to complete this operation: " + ts.Minutes.ToString() + "min " + ts.Seconds.ToString + "s"
            strMsg += "<br />Error: " + strerror
            strMsg += "<br /><br />Thank you,<br />Web Team"
            SendEmailC.SendEmail("support@carra-lucia-ltd.co.uk", "Matching Complete for Client " + clName, strMsg)
        End If
        pr.WriteToLog("Matching Finished for client " + clName, params_local(0).ToString, params_local(1).ToString)
    End Sub
End Class

You can see above that the MatchAllDocuments method accepts a single parameter of type Object (this is required for the ParameterizedThreadStart method) and that in this case that parameter will be an Object[] array containing more than one value. I prefer to email the results when completed to the user. Alternatively, you can decide to write to a file or use a session variable to store the results.

In my Global.asax.vb class, I have the following method:

<%@ Import Namespace="System.Threading" %>
 Public Shared Sub MatchClient(params() As Object)
        Dim pc As New LongProcesses
        Dim ts As New ParameterizedThreadStart(AddressOf pc.MatchAllDocuments)
        Dim thd As Thread
        thd = New Thread(ts)
        thd.IsBackground = True
        thd.Start(params)
    End Sub

Because the method is Shared, it can be accessed from anywhere in my code.
A new instance of the LongProcesses class is created on every call to the static method. Note also that the thread we create is set to be a background thread. This method call will not block – it will return almost immediately because it is not being called on the main thread.

On the main button click we have the following event:

Protected Sub btnMatchAll_Click(sender As Object, e As EventArgs)
        Dim parms() As Object = New Object(1) {cboClients.SelectedValue, Session("Username")}
        ASP.global_asax.MatchClient(parms)

        lblMessage.Text = "Matching process has been started and you will receive an email when this process is complete."
        lblMessage.Visible = True

    End Sub

The result of the button push is an immediate return to screen with a message and also an email within the next few minutes like the one below:

Email result. Confidential information has been blurred out.
Email result. Confidential information has been blurred out.

Funny Customer Support Conversations

Tech support: What kind of computer do you have?

Female customer: A white one…tech support press 1 glasburgen

 

Tech support: Click on the ‘my computer’ icon on to the left of the screen.
Customer: Your left or my left?

 

Tech support: Good day. How may I help you?
Male customer: Hello… I can’t print.
Tech support: Would you click on “start” for me and…
Customer: Listen pal; don’t start getting technical on me! I’m not Bill Gates.

 

Customer: Hi, good afternoon, this is Martha, I can’t print. Every time I try, it says ‘Can’t find printer’. I’ve even lifted the printer and placed it in front of the monitor, but the computer still says he can’t find it…

Customer: I have problems printing in red…
Tech support: Do you have a color printer?
Customer: Aaaah………………..thank you.

 

Tech support: What’s on your monitor now, ma’am?
Customer: A teddy bear my boyfriend bought for me at the 7-11.

 

Customer: My keyboard is not working anymore.
Tech support: Are you sure it’s plugged into the computer?
Customer: No. I can’t get behind the computer.

Tech support: Pick up your keyboard and walk 10 paces back
Customer: OK

Tech support: Did the keyboard come with you?
Customer: Yes
Tech support: That means the keyboard is not plugged in. Is there another keyboard?

Customer: Yes, there’s another one here. Ah…that one does work…

 

Tech support: Your password is the small letter “a” as in apple, a capital letter V as in Victor, the number 7.
Customer: Is that 7 in capital letters?

 

Customer: I can’t get on the Internet.
Tech support: Are you sure you used the right password?
Customer: Yes, I’m sure. I saw my colleague do it.
Tech support: Can you tell me what the password was?
Customer: Five stars.

 

Tech support: What anti-virus program do you use?
Customer: Opera.

Tech support: That’s not an anti-virus program.

Customer: Oh, sorry…Internet Explorer.

Customer: I have a huge problem. A friend has placed a screen saver on my computer, but every time I move the mouse, it disappears.

Tech support: How may I help you?

Customer: I’m writing my first e-mail.

Tech support: OK, and what seems to be the problem?

Customer: Well, I have the letter ‘a’ in the address, but how do I get the circle around it?

A woman customer called the Canon help desk with a problem with her printer.

Tech support: Are you running it under windows?

Customer: “No, my desk is next to the door, but that is a good point. The man sitting in the cubicle next to me is under a window, and his printer is working fine.”

 

And last but not least…

Tech support: “Okay Bob, let’s press the control and escape keys at the same time. That brings up a task list in the middle of the screen. Now type the letter “P” to bring up the Program Manager”

Customer: I don’t have a P.

Tech support: On your keyboard, Bob.

Customer: What do you mean?

Tech support: “P”…..on your keyboard, Bob.

Customer: I’M NOT GOING TO DO THAT!
* Tech Support: “I need you to right-click on the Open Desktop.”

Customer “OK.”

Tech Support: “Did you get a pop-up menu?”

Customer: “No.”

Tech Support: “OK. Right click again. Do you see a pop-up menu?”

Customer “No.”

Tech Support:: “OK, sir. Can you tell me what you have done up until this point?”

Customer: “Sure, you told me to write ‘click’ and I wrote ‘click’.”

* Customer: “I received the software update you sent, but I am still getting the same error message.”

Tech Support:: “Did you install the update?”

Customer: “No. Oh, am I supposed to install it to get it to work?”

* Customer:: “I’m having trouble installing Microsoft Word.”

Tech Support:: “Tell me what you’ve done.”

Customer: “I typed ‘A:SETUP’.”

Tech Support:: “Ma’am, remove the disk and tell me what it says.”

Customer:: “It says ‘[PC manufacturer] Restore and Recovery disk’.”

Tech Support:: “Insert the MS Word setup disk.”

Customer:: “What?”

Tech Support: “Did you buy MS word?”

Customer: “No…”

* Customer:: “Do I need a computer to use your software?”

Tech Support:: ?!%#$

* Tech Support:: “OK, in the bottom left hand side of the screen, can you see the ‘OK’ button displayed?”

Customer: “Wow. How can you see my screen from there?”

* Tech Support:: “Type ‘C:’ at the prompt.”

Customer:: “How do you spell that?”

* Tech Support: “Is your computer on a separate telephone line?”

Customer: “No.” (clicks the button to log on to our service)

Tech Support:: “Well then we can’t-”

Customer:: “It says ‘no dial tone’.”

Tech Support: “That’s because you’re on the line with me right now. You need to-”

Customer:: “No, that’s not it. It does this all the time. I just have to try a few times, and it will let me through.”

Tech Support:: “No, ma’am. It’s not even trying to dial right now because you’re on the phone with me.”

Customer: “It must be busy. I’ll try again later.”

* Tech Support:: “What operating system are you running?”

Customer: “Asus.”

* Customer: “My computer’s telling me I performed an illegal abortion.”

* Customer: “I have Microsoft Exploder.”

* Customer: “How do I print my voice mail?”

* Customer: “You’ve got to fix my computer. I urgently need to print document, but the computer won’t boot properly.”

Tech Support: “What does it say?”

Customer: “Something about an error and non-system disk.”

Tech Support: “Look at your machine. Is there a CD inside?”

Customer: “No, but there’s a sticker saying there’s an Intel inside.”

* Tech Support: “Just call us back if there’s a problem. We’re open 24 hours.”

Customer: “Is that Eastern time?”

* Tech Support:: “What does the screen say now?”

Customer: “It says, ‘Hit ENTER when ready’.”

Tech Support:: “Well?”

Customer: “How do I know when it’s ready?”