Sunday, 30 November 2014

iOS 8: Creating a Custom Keyboard in Swift

Starting with iOS 8, your applications can extend custom functionality and content beyond your app, and make it available to users while they're using other apps or the operating system. One way of extending the operating system is by creating a custom keyboard.

In this tutorial I'm going to show you how to make your own custom keyboard using Swift and the new app extension APIs. Before we do that, we are going to go over what a keyboard extension can do, what it can't do, and what it should to get approved for the App Store.

1. Overview

A custom keyboard replaces the system keyboard for users who want capabilities, such as a novel text input method or the ability to enter text in a language not otherwise supported by the operating system.

The essential function of a custom keyboard is simple, respond to taps, gestures, or other input events, and provide text in the form of an unattributed NSString object at the text insertion point of the current text input object.

After a user chooses a keyboard, it remains as the default one whenever they open an app. For this reason the keyboard must allow the user to switch to another keyboard.

There are two development essentials for every custom keyboard:
Trust. Your custom keyboard gives you access to what a user types, so trust between you and your user is essential.
A “next keyboard” key. The affordance that lets a user switch to another keyboard is part of a keyboard’s user interface; you must provide one in your keyboard. - App Extension Programming Guide
If you only need to add a few buttons to the system keyboard, then you should look into custom views for data input.

2. Requirements & Limitations

What a Custom Keyboard Can't Do
There are certain text input objects that your custom keyboard is not eligible to type into. These include secure text fields for entering passwords and phone pad objects, such as the phone number fields in the Contacts application.

Your custom keyboard does not have access to the view hierarchy of the input, it cannot control the cursor, and is unable to select text. Also, the custom keyboard cannot display anything above the top row. The system keyboard isn't limited by these constraints. For example, it shows an extension when you tap a key to show the user what key was tapped.

The red line shows the top limit of a custom keyboard.
Sandboxing
By default, a keyboard has no network access and cannot share files with its containing app. To enable these capabilities, set the value of the RequestsOpenAccess key in the Info.plist file to YES. Doing so expands the keyboard's sandbox as described in Apple's App Extension Programming Guide.

If you do request open access, your keyboard gains the following capabilities, each with a concomitant responsibility:

access to location services and the address book database, each requiring the user's permission on first access
option to use a shared container with the keyboard's containing app, which enables features, such as providing a custom lexicon management user interface in the containing app
ability to send keystrokes and other input events for server-side processing
access to iCloud, which you can use, for example, to ensure that keyboard settings and your custom autocorrect lexicon are up to date on all devices owned by the user
access to Game Center and in-app purchase through the containing app
ability to work with managed apps if you design your keyboard to support mobile device management (MDM)
Be sure to read Apple's Designing for User Trust document, which describes your responsibilities for respecting and protecting user data in case you request open access.

3. How It Works

In the most basic form we have an application that contains a keyboard extension and a UIInputViewController that controls the keyboard and responds to user events.

The Custom Keyboard template contains a subclass of UIInputViewController, which is the primary view controller of your keyboard. Let's look at the inte rface to get a feel of how it works.

class UIInputViewController : UIViewController, UITextInputDelegate, NSObjectProtocol {

    var inputView: UIInputView!

    var textDocumentProxy: NSObject! { get }

    func dismissKeyboard()
    func advanceToNextInputMode()

    // This will not provide a complete repository of a language's vocabulary.
    // It is solely intended to supplement existing lexicons.
    func requestSupplementaryLexiconWithCompletion(completionHandler: ((UILexicon!) -> Void)!)
}
inputView is the view used for the keyboard, it is the same as the view property
dismissKeyboard method can be called to dismiss the keyboard
advanceToNextInputMode is used to change between keyboards
textDocumentProxy is the object that you'll use to interact with the current text input

self.textDocumentProxy.insertText("Tuts+") // inserts the string "Tuts+" at the insertion point

self.textDocumentProxy.deleteBackward() // Deletes the character to the left of the insertion point
UIInputViewController conforms to the UITextInputDelegate protocol, notifying you when the text or text selection changes through the the selectionWillChange, selectionDidChange, textWillChange and textDidChangeevents
4. Making a Calculator Keyboard

Let's create a custom keyboard to make all this a little bit more tangible. We'll make a simple keyboard that can handle numeric input and simple operations. We're going to use a XIB file for the keyboard's user interface.

Step 1: Create a New Project
Open Xcode 6, create a new Single View Application and select Swift as the programming language. Name it CalculatorKeyboard.

Step 2: Add a Text Field
Open Main.storyboard and drag a text field from the Objects Library. We'll use this to test the keyboard later. Center the text field and add the necessary layout constraints as shown below.

If you call textField.becomeFirstResponder() in viewDidLoad the keyboard will open when you start the app.

Step 3: Add the Keyboard Extension
Select the project file in the Project Navigator and add a new target by clicking the plus button at the bottom.

Select Application Extension on the left, choose the Custom Keyboard template, and name it Calculator.

This will create a new group named Calculator, containing two files KeyboardViewController.swift and Info.plist.

Step 4: Cleaning Up
Open KeyboardViewController.swift. The template keyboard has one button, letting the user switch between keyboards. Remove the code in the viewDidLoad method.

Step 5: Creating the User Interface
Right click the Calculator group and select New File.... Select the User Interface section on the left, choose the View template, and name it Calculator. This should create a file named Calculator.xib.

Open the XIB file and, in the Attributes Inspector on the right, set the size to Freeform and the status bar to None.

In the Size Inspector set the width of the view to 320 and the height to 160.

Drag a button from the Objects Library to the view. In the Attributes Inspector, set the title to 1. In the Size Inspector, set the button's width and height to 30. Move the button to the top right corner of the view until it aligns with the margins.

Copy the button by clicking and dragging the button while pressing the Option key. Position the second button below the first one.

Select the buttons by pressing Command-A and copy the buttons. Position the new buttons below the first and second button.

Repeat the process to create another column of buttons until you have four columns of buttons.

Next, select the column on the left and make a copy that aligns with the left border of the view.

Set the width of the buttons to 140 points. Replace the top left button with a label that has the same size as the button. Rename the buttons like in the screenshot bellow.

Give the view a blueish background color and set the background color for the buttons to white with an opacity of 15%. And for the display label, make it black with an opacity of 15%. Set the text size to 18 points for every user interface object and set the text color to white. The user interface should now look like this:

Step 6: Loading the User Interface
We first need to create a property in which to store the user interface.

class KeyboardViewController: UIInputViewController {
    var calculatorView: UIView!

    ...
}
Create a method named loadInterface and call it in the viewDidLoad method of the KeyboardViewController.

class KeyboardViewController: UIInputViewController {
    ...

    override func viewDidLoad() {
        super.viewDidLoad()

        loadInterface()
    }

    func loadInterface() {
        // load the nib file
        var calculatorNib = UINib(nibName: "Calculator", bundle: nil)
        // instantiate the view
        calculatorView = calculatorNib.instantiateWithOwner(self, options: nil)[0] as UIView

        // add the interface to the main view
        view.addSubview(calculatorView)

        // copy the background color
        view.backgroundColor = calculatorView.backgroundColor
    }

    ...   
}

Step 7: Testing the Keyboard
At this point you should be able to test your new keyboard. With the CalculatorKeyboard scheme selected, build and run the application on your device. This will add a new keyboard to your device. However, before you can use it you first need to install it.

Go to Settings > General > Keyboard > Keyboards and select Add new Keyboard. There you'll find the Calculator keyboard in the list of third-party keyboards. Select and install the keyboard. The next time you open the keyboard you should be able to see your new keyboard by pressing the next keyboard button.

If you are using the iOS Simulator, the custom keyboard might not work inside your app. To see the keyboard press home and open Spotlight.

Step 8: Next Keyboard
Create a property for the next keyboard button in the KeyboardViewController class.

class KeyboardViewController: UIInputViewController {

    @IBOutlet var nextKeyboardButton: UIButton!

    ...
}
Open Calculator.xib , Select File's Owner, and in the Identity Inspector change its class to KeyboardViewController.

Right click on the Next Keyboard button and connect a referencing outlet to the File's Owner.

In the loadInterface method, we add an action to the nextKeyboard button as shown below.

class KeyboardViewController: UIInputViewController {
    ...

    func loadInterface() {
        ...

        // This will make the button call advanceToNextInputMode() when tapped
        nextKeyboardButton.addTarget(self, action: "advanceToNextInputMode", forControlEvents: .TouchUpInside)
    }

}
Step 9: Number Display
Create a property for the display and connect the referencing outlet in Interface Builder.

class KeyboardViewController: UIInputViewController {

    @IBOutlet var display: UILabel!

    ...
}
Create a method named clearDisplay and call it in the viewDidLoad method, after invoking loadInterface. The display should now show 0 when you open the keyboard.

class KeyboardViewController: UIInputViewController {
    ...
    
    override func viewDidLoad() {
        super.viewDidLoad()
        
        loadInterface()
        clearDisplay()
    }
    
    ...
    
    @IBAction func clearDisplay() {
        <span class="skimlinks-unlinked">display.text</span> = "0"
    }
}
Connect the C button's touch up inside event to the clearDisplay method in Interface Builder.

Step 10: Number Input
Time to handle numeric input. When you open the keyboard it shows 0 on the display. If you tap a number key, it should replace the display to that number. Create a property named shouldClearDisplayBeforeInserting to implement this behavior.

Create a method named didTapNumber and connect it in Interface Builder to all the number buttons for the touch up inside event. The method uses the titleLabel of the button to determine which number was tapped.

class KeyboardViewController: UIInputViewController {
    var shouldClearDisplayBeforeInserting = true

    ...

    @IBAction func didTapNumber(number: UIButton) {
        if shouldClearDisplayBeforeInserting {
            <span class="skimlinks-unlinked">display.text</span> = ""
            shouldClearDisplayBeforeInserting = false
        }

        if var numberAsString = number.titleLabel?.text {
            var numberAsNSString = numberAsString as NSString
            if var oldDisplay = display?.text! {
                <span class="skimlinks-unlinked">display.text</span> = "\(oldDisplay)\(numberAsNSString.intValue)"
            } else {
                <span class="skimlinks-unlinked">display.text</span> = "\(numberAsNSString.intValue)"
            }
        }
    }
}
Update the clearDisplay method as shown below.

class KeyboardViewController: UIInputViewController {
    ...

    @IBAction func clearDisplay() {
               <span class="skimlinks-unlinked">display.text</span> = "0"
        shouldClearDisplayBeforeInserting = true
    }
}
The keyboard code is in a different target than your app. Because of this the debug logs aren't visible. To see the logs for the Calculator target, open the system log from the iOS Simulator.

Step 11: Dot Input
The button to insert a dot should add a dot to the display, but only if there isn't a dot present yet.

class KeyboardViewController: UIInputViewController {
    ...

    @IBAction func didTapDot() {
        if let input = display?.text {
            var hasDot = false
            for ch in input.unicodeScalars {
                if ch == "." {
                    hasDot = true
                    break
                }
            }
            if hasDot == false {
                <span class="skimlinks-unlinked">display.text</span> = "\(input)."
            }
        }
    }
}
Step 12: Inserting Text
The button to insert text should add the calculator display text to the insertion point. To do this, we use the textDocumentProxy property as shown below.

class KeyboardViewController: UIInputViewController {
    ...

    @IBAction func didTapInsert() {
        var proxy = textDocumentProxy as UITextDocumentProxy

        if let input = display?.text as String? {
            proxy.insertText(input)
        }
    }
}
Step 13: Handling Operations
Because we're implementing a simple keyboard that doesn't support expression trees, 1 + 2 * 3 will equal 9. We're going to use a simpler model in which the calculator has an internal memory slot on which it can apply operations.

Let's take a simple input in order to understand how the calculator algorithm works:

user taps 1, the display should change from 0 to 1
user taps +, the calculator should remember to add the next inputted number to 1
user taps 2, the display should change from 1 to 2
user taps *, the display and the internal memory of the calculator should change to 3, the calculator should remember to multiply the internal memory with the next inputted number
user taps 3, the display should remain 3
user taps =, the calculator should apply the last operation and the display should change to 9
Observations:

the calculator should remember the next operation to apply
after inputting a number if an operation or equal is pressed, the calculator should apply the last remembered operation
if the user presses two or more operations without inputting a number, the calculator should remember the last one
after an operation is applied, the display should update with the result
after a result is displayed, the display should clear before writing another number
In order to implement the calculator, we are going to need:

an internalMemory property that stores the temporary result
a property that stores the nextOperation
another one that to remember if it should apply the nextOperation after an operation is pressed

enum Operation {
    case Addition
    case Multiplication
    case Subtraction
    case Division
    case None
}

class KeyboardViewController: UIInputViewController {
    var internalMemory = 0.0
    var nextOperation = <span class="skimlinks-unlinked">Operation.None</span>
    var shouldCompute = false

    ...
}
Create a method named didTapOperation and connect it to the operation buttons touch up inside event in Interface Builder. The method will use the button title to determine which operation was pressed.

class KeyboardViewController: UIInputViewController {
    ...

    @IBAction func didTapOperation(operation: UIButton) {
        if shouldCompute {
            computeLastOperation()
        }

        if var op = operation.titleLabel?.text {
            switch op {
                case "+":
                    nextOperation = Operation.Addition
                case "-":
                    nextOperation = Operation.Subtraction
                case "X":
                    nextOperation = Operation.Multiplication
                case "%":
                    nextOperation = Operation.Division
                default:
                    nextOperation = <span class="skimlinks-unlinked">Operation.None</span>
            }
        }
    }
}
Create and implement the computeLastOperation method.

class KeyboardViewController: UIInputViewController {
    ...

    @IBAction func computeLastOperation() {
        // remember not to compute if another operation is pressed without inputing another number first
        shouldCompute = false

        if var input = display?.text {
            var inputAsDouble = (input as NSString).doubleValue
            var result = 0.0

            // apply the operation
            switch nextOperation {
            case .Addition:
                result = internalMemory + inputAsDouble
            case .Subtraction:
                result = internalMemory - inputAsDouble
            case .Multiplication:
                result = internalMemory * inputAsDouble
            case .Division:
                result = internalMemory / inputAsDouble
            default:
                result = 0.0
            }

            nextOperation = <span class="skimlinks-unlinked">Operation.None</span>

            var output = "\(result)"

            // if the result is an integer don't show the decimal point
            if output.hasSuffix(".0") {
                output = "\(Int(result))"
            }

            // truncatingg to last five digits
            var components = output.componentsSeparatedByString(".")
            if <span class="skimlinks-unlinked">components.count</span> >= 2 {
                var beforePoint = components[0]
                var afterPoint = components[1]
                if afterPoint.lengthOfBytesUsingEncoding(NSUTF8StringEncoding) > 5 {
                    let index: <span class="skimlinks-unlinked">String.Index</span> = advance(afterPoint.startIndex, 5)
                    afterPoint = afterPoint.substringToIndex(index)
                }
                output = beforePoint + "." + afterPoint
            }

            // update the display
            <span class="skimlinks-unlinked">display.text</span> = output

            // save the result
            internalMemory = result

            // remember to clear the display before inserting a new number
            shouldClearDisplayBeforeInserting = true
        }
    }
}
Update the clearDisplayMethod as shown below. When the user starts to write the first number, the internal memory should be set to 0 and nextOperation should be addition. That way, after the user inputs the first number and presses an operation, the calculator will remember the inputted number
class KeyboardViewController: UIInputViewController {
    ...

    @IBAction func clearDisplay() {
        <span class="skimlinks-unlinked">display.text</span> = "0"
        internalMemory = 0
        nextOperation = Operation.Addition
        shouldClearDisplayBeforeInserting = true
    }
}

Advertisement
Step 14: Finishing Touches
Let's use the IBInspectable declaration attribute to add a corner radius to the buttons and display. First, create a subclass of UIButton and UILabel.

class RoundButton: UIButton {
    @IBInspectable var cornerRadius: CGFloat = 0 {
        didSet {
            layer.cornerRadius = cornerRadius
        }
    }
}

class RoundLabel: UILabel {
    @IBInspectable var cornerRadius: CGFloat = 0 {
        didSet {
            layer.cornerRadius = cornerRadius
        }
    }
}
In Interface Builder, select the buttons and change their class to RoundButton in the Identity Inspector. In the Attributes inspector, you should see the new corner radius attribute.

Do the same for the display label. Your keyboard should now look like this.

Conclusion

You should now be able to make a custom keyboard in iOS using the app extension APIs. Remember that every custom keyboard must have a way to switch to the next keyboard and that your keyboard cannot connect to the internet, access location services, or talk with its containing app by default, but you can request these capabilities.

The system will use the default keyboard for secure fields, such as password and phone number fields. Don't forget that the code for the custom keyboard lives in a separate target. Because of this the debug logs aren't visible. To see them, open the system log from the iOS Simulator.

Revisiting Open Source Social Networking Alternatives

Talk about 15 minutes of fame: upstart social networking startup Ello burst on the scene in September with promises of a utopian, post-Facebook platform that respected user's privacy. I was surprised to see so many public figures and media entities jump on board—mainly because of what Ello isn't. It isn't an open source, decentralized social networking technology. It's just another privately held, VC-funded silo.

Perhaps I'll get excited when BoingBoing posts there a second time ("we're not entirely sure what we're doing here yet") or if I get an invite; probably not.

In reality, the road to a usable open source social networking technology is paved with the wreckage of good intentions.

Remember Diaspora? In 2010, it raised $200,641 on Kickstarter to take on Facebook with "an open source personal web server to share all your stuff online." Two years later, they essentially gave up, leaving their code to the open source community to carry forward.

How about OpenSocial? "This site may be hacked."

Guess that didn't work out that well either. That was 2007, and count me among the idealists with faded dreams. I didn't even keep my blog posts up—you have to read them on Archive.org.

Even today, researching open source social networking alternatives online is a bit like reading about star couples in the entertainment tabloids; it's hard to tell who's dated who, who's on their own and who's still together.

Diaspora's still around. Identi.ca (not to be confused with Friendica) became Status.net which is now Pump.io but if you want to try it out you have to visit Ephemeral Me. There's Tent.io which you used to be able to try out at Tent.is but is now Cupcake.io. Diaspora and Tent considered getting together but decided not to. Still with me? Good, because Status.net is now part of GNU Social. There's Feedly which became the Stream Framework with SaaS commercial partner GetStream.io. And, don't forget BuddyCloud or the Activity Streams standard. And that's just branding and relationship status, it says nothing about the actual quality, viability or status of these technologies.

If you're not overwhelmed yet and haven't despondently clicked back over to check your Facebook account, someone at Wikipedia has compiled this questionably helpful comparison of software and protocols for distributed social networking. I apologize if I left out or misunderstood your awesome project but honestly folks, it's really hard for people to figure out what your technology is doing and whether it's worth investigating.

For this series, I'm going to introduce you to six of these technologies:

Diaspora
Pump.io
GNU Social
Tent.io
GetStream.io
BuddyCloud
This article will briefly walk through the state of these solutions, and in part two I'll walk you through installing the most compelling contenders.

An Overview of Current Technologies

1. Diaspora
Diaspora is written in Ruby and has a federated server model with 54 "pods" running. The latest release was in September 2014. One blogger reported that in the wake of Ello's VC funding disclosure, Diaspora usage doubled to 25,000 users.

You can sign up at any of the open pods listed here, but good luck figuring out which might be a good one to try. For example, I decided to try one of the more populous "open" pods in the US, ShrekIsLove. Here's what I found:

Kind of makes me long for a clean blue Facebook logo. Sign up is a bit smoother:

Here's what the profile configuration page looks like:

The timeline page is more friendly, although posting is a bit rough around the edges. In my opinion, "you can use Markdown to format your post" isn't really a positive thing (sorry @gruber).

Preview is integrated with geolocation and images but still a bit rough around the edges:

There's some very solid functional progress but it's still extremely rough around the edges. Diaspora certainly isn't dead, but I don't clearly see a trajectory yet towards being something I would adopt.

2. Pump.io
Pump is led by open source social networking veteran Evan Prodromou and is written in Node.js. Evan wrote Status.net but turned it over to GNU in order to focus on the new Pump.io platform.

To try Pump.io, register at Ephemeral Me. It's very clean and Twitter-like (yeah, Bootstrap):

Here's the signup page:

And, the profile signup:

Here's the posting dialog—sort of presented as if you're emailing your followers. I found the usability of the posting functionality to be a bit poor.

Here's what the stream looks like. I didn't see any activity here, so it wasn't clear how to connect with others or build my network:

This is the second time I've tried out Pump.io and each time I've been a bit underwhelmed. They've done some solid work but the end-user experience isn't yet at a level that draws me in.

3. GNU Social
GNU Social evolved from Prodromou's Status.net project and other GNU code. It's written in PHP, which I think is helpful for sustaining open source participation.

Some of the public networks you can join are Quitter (in various countries):

Here's the signup page:

The timeline interface was surprisingly clean and functional. I could very quickly find other people as well. Posting was super simple but with limited functionality. This is currently a Twitter-clone.

I was pleasantly surprised by how clean the interface was. By trying to be simply Twitter-like, I think they've done a solid job providing some of the basic features in a federated social network.

4. Tent.io
Tent is a public API with primary implementations in Ruby; I was also able to find secondary implementations in PHP. It was difficult to determine the status of Tent implementations, both servers and client. From what I can tell, there is no stable reference server code available yet. But Tent aspires to be more than many of the other platforms, as you'll see.

To try out Tent, you have to visit Cupcake.io (are you starting to notice that no one in this space thinks deeply about branding?):

Here's the profile page—notice the navigation on the left:

Here's the timeline and posting functionality. A relatively clean Twitter-like presentation:

Here's an example of where Tent goes beyond the others, e.g. file sharing:

And I liked that they have an API console of sorts built into their client:

The usability of Tent's Cupcake client was by far the cleanest and best-organized of all the platforms. However, I find their documentation and links to code to be quite incomplete and confusing in their lack of specifics. Exhibit A: their blog has virtually no content. I think the work here has merit and potential, but their communication needs to improve. I just wasn't sure where to engage. In fact, I was a bit concerned that any engagement would be wasted.

5. Commercial Open Source Approaches
I decided to check out a couple of platforms that emphasize the commercial aspects of their work while offering it via open source. The results were mixed.

a) GetStream.io

GetStream.io has a beautifully designed site and an excellent tutorial and documentation for using their API. The founder Thierry even sent me a nice email with links to some pertinent libraries after I signed up, which showed positive engagement.

While they clearly link to their open source Python Stream Framework, their emphasis seems to be helping people use their hosted platform to build private label social networks. To me, this is less interesting than the approach of other platforms which are federated and largely open source by design:

Check out their API tutorial, it's a nice piece of educational design:

They provide examples for different languages of how to work with the API, and show the effect on an imaginary mobile app:

b) BuddyCloud

BuddyCloud offers its work open source and provides an API, but again it appears to lack an emphasis on federation.

You can demo BuddyCloud here:

The design didn't appeal to me:

What Have We Learned

First, let's give kudos and a shoutout to all these folks and the people who I didn't have time to include. Taking back social networking into the open source fold is extremely important, and these people have put real heart, time and effort into building solutions, many viable.

They've also done a great job emphasizing data ownership, APIs, and open source. The effort they've put in to building decentralized systems is hugely important.

There are some areas that I feel are still weak all around:

Communication and documentation to describe what they're doing, its status, what technologies and standards they adhere to, and product roadmaps.
Clarifying what their aspirations are for decentralization and interoperability with other networks.
Doing well at the most important elements of the user experience, such as posting and timeline. The simplicity of posting to Facebook is one of the things that makes it work so well. There's very little sophistication on the client-side, e.g. Javascript/AJAX, with most of these tools. There needs to be much more; Ghost's interface efforts would be a model to learn from.
In the next part of this series, I'll highlight approaches that I think will be needed for the open source community to succeed at social networking. And I'll walk you through installing the best of these technologies.

If you have any feedback, suggestions, or corrections, please post them in the comments. I'd especially like to hear if I missed any important technologies.

Saturday, 29 November 2014

free domain with dns

One of our core philosophies at iWantMyName is openness. For example, we we don't force you to use our nameservers and DNS hosting services for your domain names. It might even make perfect sense to seperate domain registration and DNS hosting in some cases. That's why you can always update the nameservers of your registered domains in real-time through your online dashboard to host it somewhere else.
There are many free DNS hosting services out there and depending on the level of service or amount of domains (some of them offer paid account upgrades) they might already be sufficient for your needs. Some of the most popular ones are:

Thursday, 27 November 2014

Google introduce smart spoon

Google's Smart spoon reduces hand tremors by 76 pc and will help people suffering from Parkinson's disease.

Google has introduced a "smart spoon" aimed to help people suffering from essential tremors and Parkinson's disease. The company states that the product can reduce shaking of the spoon bowl by an average of 76%.

Internet giant Google has started promoting its Liftware spoon, a high tech device that employs hundreds of algorithms to sense how a hand is shaking and makes instant adjustments to stay balanced. The spoons have been launched for $295.

Parkinson's disease affects more than 10 million people worldwide, including Google co-founder Sergey Brin's mother. According to reports Brin has also said he has a genetic mutation associated with higher rates of Parkinson's. He has donated more than $50m to research for a cure.

"We want to help people in their daily lives today and hopefully increase understanding of disease in the long run," Google spokesperson Katelin Jabbari said.

Earlier this year, Google had acquired Lift Lab, the spoon's maker. The company's founder, Anupam Pathak and his team now work for Google X's life sciences division.

Pathak states that they hope to add sensors to the spoons to help medical researchers and providers better understand, measure and alleviate tremors.

Apart from this the division has made major acquisitions in medical field. The division owns a stake in DNAnexus, a software company analyzing genome sequencing to better understand the genetic factors of heart disease and ageing. Google's X's life sciences division is also working on smart contact lens that would measure glucose levels in tears to help diabetics track their blood sugar levels and is researching on how nanoparticles in blood might help detect diseases. Read: Google partners with Novartis to produce 'smart' contact lenses

Tuesday, 25 November 2014

Nokia new comback with tab

Just when we thought that Nokia was done as an independent manufacturer, the Finnish brand surprised us by announcing a new tablet which runs on Android 5.0 Lollipop. The N1 Tablet looks like a decent comeback for Nokia and the device itself looks elegant with a similar design to the iPad mini.

According to sources, the tablet is design by Foxconn (the same company that makes Apple products), features a 7.9-mm display with a resolution of 2048x1536 pixels, and is powered by a quad-core Intel Atom Z3580 64-bit SoC. It comes with a unibody design and is quite slim at just 6.9 mm. The price for the tablet has been put at $249 (Rs. 15,300 approx.) which sounds impressive. The tablet surprisingly runs on Android 5.0 Lollipop with the Nokia Z Launcher over it. Nokia says that it will brought to the market in Q1 2015 through a brand-licensing agreement with an original equipment manufacturer (OEM) partner responsible for manufacturing, distribution and sales.

Here are some interesting features of the tablet:

Windows 8 touch optimised health app and how to optimise it

Many people take medication, sometimes multiple times per day, to help them stay healthy. Making sure meds are taken on time and in the right doses requires an individual to be vigilant and disciplined. Software developer Tim Corey saw a way to improve the error-prone process of tracking self-medication by using technology to provide an easy-to-use personal medication assistant, one that never forgot a dose and had a perfect memory. This idea led to his creation of My Health Assistant.

My Health Assistant is an app that helps individuals manage and track their medication use through a simple interface. The app also features a health diary, a GPS-based pharmacy and ER locator, and personal health information.

Corey developed My Health Assistant as an entry in the Intel® App Innovation Contest 2013 hosted by CodeProject in partnership with the Intel® Developer Zone, and the app went on to win in the Health Category. The app was initially built for Microsoft Windows* desktop, with the ultimate target of Windows-based tablets, such as the Lenovo ThinkPad* Tablet 2, Ultrabook™ 2 in 1s running Windows 8.1*, Windows Phone* 8, and other mobile platforms.

Corey's central development goals were portability, usability, and security. To reach these goals, he had to overcome a number of challenges throughout development, including implementing cross-platform touch UI and securing sensitive medical data. This case study explores those challenges, the solutions Corey applied, and the resources he used.

Corey took a modular approach to building the app, working on each piece of functionality separately in C# and wiring them together with the XAML Windows Presentation Foundation (WPF) UI using the Model View ViewModel (MVVM) design pattern.

Choosing C#

Prior to making My Health Assistant, Corey had considerable experience working with the object-oriented .NET programming language C#. He chose C# as the main language for building the app (using Microsoft Visual Studio*) for a number of reasons, including Microsoft's support behind it, which brings an entire ecosystem of tools, libraries, and other resources.

As a key approach to creating a cross-platform app, C# can also be taken into practically any environment: from PC, Linux*, or Apple Mac* to Apple iPhone* or Google Android*. An additional strength of C# is that security and encryption are incorporated deeply in the code, removing what otherwise could be a big hurdle, especially when dealing with sensitive data such as medical records.

Corey considered other language options such as VB.NET, another .NET language, and also Java*. However, in Corey's opinion, none of them offered the same combination of familiarity and features that C# was able to provide.

C# Libraries

The Microsoft ecosystem around C# includes a large number of optimized libraries that Corey believes greatly simplify the coding process. In My Health Assistant, the app's data is stored in XML files for ease of cross-platform portability, and because of the way the libraries have been incorporated into the programming framework, Corey was able to write one simple line of code and have all of that data taken care of.

In addition to the Microsoft libraries, many third-party libraries are available for C#. For the UI framework of My Health Assistant, Corey used the Caliburn.Micro, which enabled him to connect the app's front- and back-end code using MVVM. This approach allowed flexibility when editing the UI, removing the need for comprehensive recoding after making any modifications.

WPF UI

To build the UI, Corey chose the Microsoft WPF system over Windows Forms because of its responsiveness to screen size changes, a vital ingredient of cross-platform development. With Windows 8 desktop and Windows Phone 8 both using WPF, Corey was quickly able to produce different versions of the app for each platform without major UI recoding.

In practice, the responsive WPF UI serves up elements in a particular number and size according to the available screen real estate. A full desktop view will display the full complement of buttons, whereas a mobile view will show only one or two with the others moved to a drop-down menu.

Overcoming Touch and Scrolling Problems

Any app for portable devices, whether for smartphones, tablets, or Ultrabook devices, needs effective touch controls. While the desktop app works well with a mouse, Corey specifically designed it for touch, ensuring that simple actions such as scrolling through a menu worked well with a single finger. He even disabled the scroll bar to encourage finger scrolling.

The biggest hurdle that Corey faced during development was implementing the menu scrolling in the touch UI. The app needed to be told precisely the screen orientation and the size of the available screen real estate for menus and other elements; otherwise the app would assume that more space was available, rendering key elements such as menu buttons invisible and hence useless.

To enable touch scrolling in WPF, Corey added an attribute to the ScrollViewer that indicates the PanningMode, as in the code snippet below.

GPS Locator

One main feature of My Health Assistant is its ability to help users find the closest pharmacy or emergency room wherever they are. This feature uses the device's GPS functionality and the Google Maps* API combined with relevant location data pulled in through an API to serve up accurate and relevant information on maps.

Figure 2: Google Maps* API integration lets users easily locate their nearest pharmacy or ER.

The code below is the class that holds the GPS code, which is responsible for acquiring the coordinates and raising an event once they have been located. It is an asynchronous transaction, which means that the app continues running normally while the coordinates are located.

The following section of code calls the GPSLocator class and serves up the coordinates asynchronously. This code also provides the option of continuously acquiring new GPS coordinates, but, in the case of My Health Assistant, Corey assumed that the user would be stationary and hence would need only one set of coordinates. However, the GPS service could be left running to provide continually updated coordinates.

API Integration

For serving up local information on pharmacies and hospitals, Corey knew that choosing the right API was critical, because My Health Assistant had to be able to provide accurate information anywhere in the world, not just the United States. Corey considered several potentially good APIs, including the Walgreens and GoodRx APIs, but had to discount them because they didn't work outside the United States. Corey ultimately chose the Factual Global Places API database, which contains global information. He was able to test its effectiveness while at a conference in Spain: a request for the nearest pharmacies produced a list of places within a couple of miles of his location.

Figure 3: Users can store their personal doctor, pharmacy, and insurance information in the app.

Alongside portability, Corey cites security as the second key pillar of the application. The app's default setting is to store data locally, which presents a relatively low security risk. However, during testing Corey found that users wanted the ability to access the stored data when using the app on different devices, which implied a cloud-based data storage solution and hence increased risk.

For cloud backup of the XML data files, rather than implement a complex API-driven solution into the app itself, Corey took the simpler route of adding cloud-based save options into the File Explorer view alongside local options. This approach made data backup intuitive while relying on encryption and the user's own trust in the service of their choice for the security of the data, whether that be Microsoft SkyDrive*, Dropbox*, Box.net, or another service. The screen shot below shows how the cloud-storage save options appear in File Explorer view.

Figure 4: Users can back up data locally or directly to their chosen cloud service using File Explorer.

Initially, Corey had difficulties with the backup functionality, having started down the path of implementing a complex storage and retrieval mechanism for the XML files. However, a friend gave him a simple yet powerful piece of code, which immediately solved the problem.

All of the app's data is saved to XML files that are then loaded at runtime to repopulate the application with the data. Below is the code that actually saves the data.

Below is the code that subsequently loads the data.

The way the code works in the app is simple. First, the following command is used to save data stored in a class to an XML file on disk.

The command below is used to load the data back into the class from the XML file, for example, when the application is launched and it needs to bring the data back in.

Testing

Corey's first line of attack when testing the app during the early stages of development was to come up with as many bad inputs as he could think of. At various stages he handed the app to several friends and family members, which proved to be an effective way to identify issues from an unbiased user perspective and refine the UI and overall usability.

The modular development approach made the process of rearranging the UI particularly quick and straightforward, allowing rapid iteration in response to feedback Corey received.

A number of UI bugs caused problems, particularly with the scrolling, which initially didn't work in the way that Corey had expected. Another bug he fixed occurred with the medication dosage counter. For example, a 6-hour countdown for one medication would then cause the countdown for the subsequent medication to begin at 5 hours 59 minutes instead of 6 hours.

Corey describes the debugging process as rough and long-winded, in contrast to the more satisfying process of actually building the app itself, but he has yet to encounter an issue for which he couldn't find a solution.

Next Steps

At the time of this writing, Corey is targeting a summer 2014 release for My Health Assistant. The initial launch will be for Windows 8 Desktop, followed by Windows Phone 8 and then other mobile platforms, including iOS and Android. Post-launch, Corey looks forward to gathering user feedback and using that feedback to iterate and improve the app over time.

Another feature that Corey is investigating is the integration of a medication lookup API to provide users with information about particular pharmaceutical drugs and where to find them at the best prices. GoodRx is an example of an API that provides this within the United States, but the search is ongoing for a solution that is effective worldwide.

Conclusion

Knowledge Growth

While Corey had worked with XAML prior to My Health Assistant, most of it was on a much simpler level. Working on the app allowed him to significantly grow his XAML knowledge and learn how to design and build better apps for the future.

In addition to XAML, Corey also greatly expanded his working knowledge of Caliburn.Micro, the framework that Rob Eisenberg created for WPF and XAML. Despite a relatively steep learning curve, Corey considers the knowledge he has gained invaluable in terms of how to make things work within the disconnected framework environment.

Key Learnings

When giving advice to his software development students, Corey emphasizes the need for good planning-an approach to development that has been reinforced through his work on My Health Assistant. The experience taught him that more time spent in the design phase means less in development and debugging.

During the design process, which involved a lot of iterating on paper, Corey frequently threw things out. Casting aside ideas and features would have been more difficult to do in the development stage resulting in wasted time. Iterating during the preliminary design phase proved to be much more efficient.

Corey also learned the danger of making technical assumptions about how things would work and not testing them prior to coding them into the app. A number of times during development, Corey found that certain things, such as scrolling, didn't behave in the way he expected, resulting in having to discard the code. Corey recommends building small applications throughout the development phase to test assumptions regarding specific functionality and behavior.

About the Developer

Tim Corey began his career as a software developer and IT professional in the late 90s, with roles as a programmer and IT director. In 2011 Corey graduated from South University with a bachelor's degree in IT and Database Administration. Subsequent roles have included lead programming analyst for an insurance group. Corey is currently the lead technical consultant at Epicross consulting firm, his own business, which aims to help organizations achieve greater IT efficiency through the optimization of their existing technology. He also teaches software development.

Building an multitouch enabled music application

Innovations in computing form factors such as All-in-One (AIO) and tablet devices that combine desktop-like performance with multi-touch-enabled, high-resolution screens are giving people fun new ways to experience making music and giving new meaning to the often-said statement that music is a universal language.

Recognizing this trend, TheBestSync, a China-based software company focused on integrated software and hardware solutions, entered the Intel App Innovation Contest 2013 (Intel AIC 2013) in partnership with Intel® Developer Zone with the idea of combining game and music technology with an AIO device to create an exciting new way for people to play and enjoy music.

TheBestSync and its CEO, Alpha Lam, have been on a mission to create innovative, interactive experiences for the entertainment market for the last three years and are no strangers to Intel Developer Zone contests. They recently took the grand prize in the Intel® Perceptual Computing Challenge with their submission, JOY*, one of the first virtual music instruments built using the Intel Perceptual Computing SDK (now the Intel® RealSense™ SDK). JOY not only won the Challenge, but it also became the inspiration for TheBestSync's most recent app submission, Paint Your Music, into the AIC 2013 contest, which won the Entertainment category for AIO devices running Microsoft Windows* 8.1.

Created specifically for the Intel AIC 2013, which challenged contestants to "Dream up an interactive entertainment experience that helps make the all-in-one an endless adventure," Paint Your Music (PYM) combines multi-touch, multi-player-enabled interaction with a musical matrix game board, virtual "paint balls," and a scoring mechanism to create a unique, fun-to-play virtual musical instrument/game.

As Intel AIC 2013 finalists, TheBestSync received a Lenovo IdeaCentre Horizon 27* Table PC AIO to code PYM on. The system consisted of a 27-inch 10-point touch screen, Windows 8.1, an Intel® Core™ i7 processor, 8 GB RAM, and NVIDA GPU.

Lam and TheBestSync team were excited by the Lenovo AIO's gigantic touch screen, which played a key role in PYM. The touch screen has the ability to lay flat, giving players an arcade-style, table-top game experience. "Being able to lay it flat was especially helpful," he said. "Having such a large touch screen lets multiple people engage with it at the same time, so it's very conducive to creating immersive environments. Plus, the Lenovo's 8-cell lithium-polymer battery lets users run the device for up to two hours, adding a dimension of mobility to an otherwise large device."

The AIO's high-fidelity audio capabilities further enhance gameplay, which allows users to create their own music.

In "recreational" single-player mode, PYM functions as a virtual 3D musical instrument. Using touch, the player places "music note balls" on a matrix. Music note balls act as graphic representations of notes and behave like virtual paintballs, triggering notes and "paint dances." The AIO's multi-touch-enabled screen lets the player position notes with one hand and "spin" the matrix in 3D space (Figure 1).

Figure 1: In single-player mode, notes are positioned on a matrix by touching the screen. Users can change the angle of view in 3D space, where notes appear as pillars of color or animated "paint dances."

In "competitive" two-player mode, players launch music note balls toward their opponents' "music wall." As the balls land on the matrix they produce notes. Melodies result as more notes are launched over the course of a game. Points are scored when "props" are stuck by a ball. All the music is created on-the-fly in real time and can be recorded and played back to make music.

PYM was built using the Unity 3D Engine*. Programming was handled with Microsoft Visual Studio* and C#, an object-oriented language that the team preferred over C++ because of its seamless compatibility with Unity. For PYM's audio capabilities, TheBestSync team used the interactive framework they refined while developing JOY. The framework is based on the audio engine that ships with Unity and includes additional digital signal processing audio effects, such as reverb and echo (delay), as well as the ability to record and play back music created during gameplay.

Before founding TheBestSync, Lam spent a decade running a music production house, which afforded the PYM development team ready access to an extensive, proprietary library of instrument sounds that they were able to plug into Unity's step sequencer. The library supports high-fidelity 16-bit, 24 kHz MP3 and WMA sound files as well as 24-bit, 48 kHz WAV files that were created using Avid Pro Tools* and Apple Logic* Pro digital audio workstation software.

Figure 2: Paint Your Music's multi-player UI. (A) The music matrix. (B) Music note balls. (C) Red player "prop" launcher. (D) Blue player music wall. (E) Elapsed time display and a menu for accessing settings, choosing what kind of applause you'll hear, and other items.

PYM's user interface combines 2D and 3D assets. The 3D content was produced using Autodesk Maya*, and to simulate "paint dances," the team used Unity's particle system and physics engine.

Achieving a balance between great-looking visuals and real-time performance proved to be the team's biggest challenge. The particle system was particularly thirsty for CPU horsepower. To achieve higher frame rates, PYM's code took advantage of both the on-chip GPU in the Intel Core i7 processor and the Lenovo AIO's NVIDIA GPU (Figure 3). To further boost performance, the team reduced the number of simultaneous particles from 2,500 to about 1,000 and adjusted the size and texture of the particles.

Figure 3: Paint Your Music achieves 9 fps playback with the NVIDIA GPU engaged (left) and 15 fps when both the NVIDIA GPU and Intel® HD Graphics are used (right).

In addition to fine-tuning the particle system, TheBestSync team used multi-threading to enable PYM to run multiple processes-graphics, sound, physics-across multiple cores and threads. "PYM's real-time 3D graphics and music would not have been possible without the Intel® processor built into the Lenovo AIO platform," said Lam.

Multi-touch support was another hurdle that TheBestSync had to overcome. The Unity 3D engine doesn't support multi-touch natively, so the team used C# to script a plug-in that references the Windows 8 Touch API. The team followed Microsoft's suggested best practices for setting touch-target sizes. "The Lenovo all-in-one's touch screen is huge, so while the size of touch-targets can be problematic on small form-factor devices, it wasn't an issue for us," said Lam.

Multi-touch support was another hurdle that TheBestSync had to overcome. The Unity 3D engine doesn't support multi-touch natively, so the team used C# to script a plug-in that references the Windows 8 Touch API. The team followed Microsoft's suggested best practices for setting touch-target sizes. "The Lenovo all-in-one's touch screen is huge, so while the size of touch-targets can be problematic on small form-factor devices, it wasn't an issue for us," said Lam.

Intel® Graphics Performance Analyzers (Intel® GPA) was used to diagnose and debug PYM. Intel GPA's ability to display CPU and GPU usage visually helped the team quickly identify bottlenecks in the Microsoft DirectX*-based graphics pipeline. The team used Unity 3D's Profiler window to handle the general debugging of code related to memory usage, audio, physics, and rendering.

Formal, commercial-level beta testing has not yet been conducted.

TheBestSync plans to launch PYM by the end of 2014. Its goals include:

In addition, Lam hopes to add support for OpenGL* and OpenGL ES* to enhance the graphics pipeline's performance on mobile platforms.

Another feature the company plans to implement is in-app purchasing using different device-specific payment SDKs. Currently, TheBestSync uses the Microsoft Azure* platform for distributed cloud services, but they're investigating alternatives such as the Amazon Web Services cloud platform.

Distribution will be handled through the Microsoft App Store and other similar app stores.

Lam is considering migrating PYM to other mobile platforms, which will present new challenges, not the least of which is scaling the app's UI and graphics to accommodate small form-factor devices and screens, devices of varying capabilities, and other fragmentation issues.

Alpha Lam studied applied electronics and spent 10 years in music production before founding TheBestSync. The company currently employs 20 people. The PYM team included three software developers, three 3D graphics programmers, and an audio engineer.

Google to host online shooping

For first time buyers, Google has featured a special section that features every product at Rs. 299. Google is also conducting several contests before the annual shopping festival.

Google's annual online shopping festival, also known as Great Online Shopping Festival (GOSF), is scheduled to be held between December 10-12. This year's GOSF features over 450 partners with brands ranging from Motorola Nexus 6, HP, Lenovo, Tata Housing, Karbonn, Van Heusen, Asian Paints

For first time buyers, Google has featured a special section that features every product at Rs. 299. The section has brands such as Uber, JBL, Benetton, Alia Bhatt collection, EverPure water purifier. Google is currently running several contests and games on the official websites to promote the festival. Customers stand a chance to win 14 minutes of free shopping hosted by leading brands.

Users will be able to participate in this contest across leading social media platforms from 25th November till 8th of December 2014. #WinGOSF2014. The contest is hosted by 14 brands like Asian Paints, Jet Airways, Kindle, Micromax, HP, Ask Me, CraftsVilla, Cox & Kings, Goibibo, Big Bazaar, KOOVs, Trendin, Lakme and Lenovo.

Google had launched the initiative in 2012. "... (GOSF) has seen tremendous response with most players seeing over 350 percent growth in daily sales. Last year, 2 million users visited gosf.in and over 16 million users visited across all partner sites including smaller players registering 2x growth on an average in their daily sales," says Google in a release.

Speaking about the momentum of online shopping in India, Rajan Anandan, VP & Managing Director, Google India said, "Great Online shopping festival is India's version of cyber Monday and is an exciting platform to move the industry forward. The consumer confidence to shop online has grown considerably in the last 12 months, boosting the growth of both large multinational and homegrown companies. Our recent report projects that the Industry will continue to see robust growth in next few years making it a USD 15 billion industry by 2016."

Online shopping has tremendously grown in India. Over the last few months, brands have taken online-exclusive route to sell their products. Google's recent study on e-commerce in India reveals the online shopping market in the country will grow to $15 billion by 2016. Also read: 6 important takeaways from Google's study on e-commerce in India

Google's online shopping festival is said to be inspired by Cyber Monday. Of late, we've seen Indian e-commerce giants such as Flipkart and Snapdeal trying to mimic the model in India. Also read: The Monday mega online sale: 3 important takeaways

Are you excited about Google's great online shopping festival? What are your expectations?

Charge a phone battery in 30 seconds

TEL AVIV: An Israeli company says it has developed technology that can charge a mobile phone in a few seconds and an electric car in minutes, advances that could transform two of the world's most dynamic consumer industries.

Using nano-technology to synthesize artificial molecules, Tel Aviv-based StoreDot says it has developed a battery that can store a much higher charge more quickly, in effect acting like a super-dense sponge to soak up power and retain it.

While the prototype is currently far too bulky for a mobile phone, the company believes it will be ready by 2016 to market a slim battery that can absorb and deliver a day's power for a smartphone in just 30 seconds.

"These are new materials, they have never been developed before," said Doron Myersdorf, the founder and chief executive of StoreDot, whose investors include Russian billionaire and Chelsea soccer club owner Roman Abramovich.

The innovation is based around the creation of "nanodots", which StoreDot describes as bio-organic peptide molecules. Nanodots alter the way a battery behaves to allow the rapid absorption and, critically, the retention of power.

The company has raised $48 million from two rounds of funding, including backing from a leading mobile phone maker. Myersdorf declined to name the company, but said it was Asian.

With the number of smartphone users forecast to reach 1.75 billion this year, StoreDot sees a big market, and some experts think that -- with more work -- it could be on to a winner.

"We live in a power hungry world ... people are constantly chasing a power outlet. StoreDot has the potential to solve this real big problem," said Zack Weisfeld, who has worked with and evaluated ventures in the mobile phone sector globally.

"They still have some way to go, to deal with size of battery and power cycle rounds, but if solvable, it's a very big breakthrough," he told Reuters. A power cycle round refers to the number of times a battery can be re-charged in its lifetime.

Myersdorf said a fast-charge phone would cost $100-$150 more than current models and would ultimately be able to handle 1,500 recharge/discharge cycles, giving it about three years of life.

Windows 8.1 error recivery

A s with the release of any new operating system, some users have experienced problems installing and running Windows 8.1 and Windows RT 8.1.

On this page we'll report the most serious bugs or upgrade problems and offer potential solutions. Help us and fellow readers identify and fix other problems using the comments facility at the foot of the article.

Windows RT 8.1 BSOD

The most serious bug reported so far affects Windows RT 8.1, with some users experiencing the dreaded Blue Screen of Death or Boot Configuration Data File errors after installation.

The problem is so severe that Microsoft has decided to pull the Windows RT 8.1 update from the Windows Store.

Many users have been unable to repair devices affected by the Windows RT 8.1 update, so Microsoft has released a Surface RT recovery image to help restore tablets to working order. Beware that clicking on that link will immediately instigate the 3.8GB download.

It's not yet clear when Microsoft will release a patched version of the update. (Update 23 October: Microsoft has re-released Windows RT 8.1 in the Windows Store.)

Windows 8.1 installation snags on drivers

The upgrade installation of Windows 8.1 stalled on one of our office machines because of a driver issue. Windows demanded that we uninstall "Sentinel Runtime Drivers" before the installation could proceed, but there was no obvious means of removing them via the Add/Remove Programs facility.

We found that following the instructions published by SuperUser.com solved the problem.

Remember that if you're copying the address of the downloaded file into the Command Prompt, you can't use the normal cut and paste keyboard shortcuts. Instead, use the Paste facility in the dropdown File menu of the Command Prompt.

SkyDrive files available "online only"

If you'd synchronised desktop files on your PC with SkyDrive before installing the 8.1 update, you may have been shocked when you first looked into your SkyDrive folder to discover folders now marked as available "online only".

On our test office PC, this label proved misleading. Files stored inside folders that were ostensibly "online only" were still available even when we disconnected from the internet, and the local file storage afforded to SkyDrive suggests those files are indeed still saved locally.

Microsoft's support site claims that: "The SkyDrive files you've saved or previously opened on your PC are automatically available offline on that PC. Any files you create on SkyDrive.com or another computer are online-only to save space on your PC."

To avoid any confusion, open Windows Explorer, right click on "SkyDrive" in the left-hand pane and click "Make available offline". All your files should now be synchronised locally, if they weren't already.

Limited upgrade path from Windows 8.1 Preview

This issue is not a bug: it's a pre-announced problem for those who jumped early and installed the Windows 8.1 Preview on their PC. Although you can upgrade in-place from the Preview to the final code, you may have to reinstall all your desktop and Windows Store apps.

Unofficially, our very own Darien Graham-Smith has written a blog post explaining how you can upgrade in-place from the Windows 8.1 Preview to final code and keep all your data, settings and programs intact. Several readers have reported on the comments below the blog that the method has worked for them, but we offer no guarantees, nor technical support if it goes wrong.

Can't find System Backup?
Also for people who didn't try the preview looking for System Backup to save a Full System Image post upgrade of their computer it has been moved.

You now have to go through the File History Control Panel entry. There is a link in the bottom left corner of the File History window to access the old Windows 7 System Backup utility.
By mr_chips on 21 Oct 2013
Another Skydrive issue
Previously I'd shunned logging in with my Live account but it seems you can't use Skydrive in 8.1 unless you do this. I gave in and connected my login to my live account in the end, but I'd be curious to know if there's a work around.
By jgwilliams on 21 Oct 2013
Network Driver issues...
I'd been running 8 on an old Acer Travelmate 6292 with no problem...upgraded to 8.1 and suddenly my network devices (both hard and wifi) said not enough resources available. plugging in a usb dongle works fine though.
By MDSmith71 on 21 Oct 2013
What about the watermark for if UEFI is disabled?

Also, can anyone confirm if a 'generic key' is a good way to install W8.1 if you want to do a clean install using a W8 key?

I want to clean install 8.1 as I have other compatibility issues which really needs a clean install and I don't want to p*** about with two/three different OSs.
By tech3475 on 21 Oct 2013
* secureboot, not UEFI.
By tech3475 on 21 Oct 2013
Fuzzy Text
Since installing 8.1 the text in Explorer and MS Office 2013 windows has become fuzzy. Googling, I can see reports of problems (but no solution) in Win 8.0 relating to Clear Typre -- but I had no issues until 8.1. It is pretty horrd so I'd be grateful if anyone has found a work around.
By speedykit on 21 Oct 2013
Fuzzy Text Fixed
Having failed to find the solution last night I found it straight after the above post. If anyone else needs the fix it's at: http://www.askvg.com/fix-bold-blurry-or-hard-to-re
ad-font-problem-in-windows-8-1/
By speedykit on 21 Oct 2013
US Recovery Image?
The link you posted appears to be for a North American Recovery Image; have they not released a specific UK version?
By nrmsmith on 21 Oct 2013
Skydrive
@jgwilliams
I've ben using a utility called syncDriver that supports using Skydrive logging in with a local account
By MikeC2 on 21 Oct 2013
European Surface RT
http://www.microsoft.com/en-gb/download/confirmati
on.aspx?id=40810# Downloads the European version of the recovery image
By DALT42 on 22 Oct 2013
Start screen not coming up after update
I have upgraded my HP Pavilion laptop to Windows 8.1 yesterday. Now the start screen is not visible. Only a black screen is visible with cursor continuously blinking. This is the same after several restarts. While upgrading to 8.1, I have gone past all steps including the verification code. Please help how to resolve this?
By Jithesh on 22 Oct 2013
Windows Transfer Wizard issue
In parallel with upgrading a bunch of 5 machines to 8.1 (all of which went without a hitch), I also bought a new desktop with a plan to move my account from an older machine.
It turns out that the Windows Transfer Wizard is only partly functional under Win8.1 - there is no option to declare a machine as the 'Old' one, so you can't create the transfer file on a PC that has been upgraded.
Equally, when importing an existing file (from Win7) it will re-establish the files but not any of the user settings.

How To Access Advanced Startup Options in Windows 8 or 8.1

The Advanced Startup Options menu in Windows 8 is the central fix-it location for the entire operating system.

From here you can access Windows 8 diagnostic and repair tools like Refresh Your PC, Reset Your PC, System Restore, Command Prompt, and much more.

Advanced Startup Options is also where you access Startup Settings, the menu that includes Safe Mode, among other startup methods that could help you access Windows 8 if its having problems starting.

The Advanced Startup Options menu should appear automatically after two consecutive startup errors. However, if you need to open it manually, there are six different ways to do so.

The best way to decide which method to use to open Advanced Startup Options is to base your decision on what level of access you have to Windows 8 right now:

If Windows 8 starts normally: Use any method, but 1, 2, or 3 will be easiest.

If Windows 8 does not start: Use method 4, 5, or 6.

Method 1 will also work if you can at least get to the Windows 8 logon screen.

Difficulty: Easy

Time Required: Accessing Advanced Startup Options can take anywhere from a few seconds, to a few minutes, depending on which method you use.

Applies To: All of these means of getting to the Advanced Startup Option menu works equally well in any edition of Windows 8 or Windows 8.1.

Method 1: SHIFT + Restart

Hold down either SHIFT key while tapping or clicking on Restart, available from any Power icon.

Tip: Power icons are available in Windows 8 from either the Settings charm or from the logon/lock screen.

Note: This method does not seem to work with the on-screen keyboard. You'll need to have a physical keyboard connected to your computer or device to open the Advanced Startup Options menu this way.

Wait while the Advanced Startup Options menu opens.
Method 2: PC Settings

Swipe from the right to open the charms bar.

Tip: If you have a keyboard, use WIN+I and then skip to Step 3.

Tap or click on Settings.

Tap or click on Change PC settings at the bottom of the charms bar.

Choose Update and recovery from the list of options on the left of the PC settings window.

Note: Prior to Windows 8.1, choose General instead and then skip to Step 6.

Choose Recovery.

Locate Advanced startup, at the bottom of the list of options on your right.

Tap or click on Restart now.

Wait through the Please wait message until Advanced Startup Options opens.

Method 3: Shutdown Command

Open Command Prompt in Windows 8.

Tip: Another option is to open Run if you can't get Command Prompt started for some reason.

Execute the shutdown command in the following way:
shutdown /r /o

Note: Save any open files before executing this command or you'll lose any changes you've made since your last save.

To the You're about to be signed off message that appears a few seconds later, tap or click on the Close button.

After several seconds, during which nothing seems to be happening, Windows 8 will then close and you'll see a Please wait message.

Wait just a few seconds more until the Advanced Startup Options menu opens.
Method 4: Boot From Your Windows 8 Installation Media

Insert a Windows 8 DVD, or a flash drive with the Windows 8 installation files on it, into your computer.

Tip: You can borrow someone else's Windows 8 disc or other media if you need to. You're not installing or reinstalling Windows 8, you're just accessing Advanced Startup Options - no product key or license breaking required.

Boot from the disc or boot from the USB device, whatever your situation calls for.

From the Windows Setup screen, tap or click on Next.

Tap or click on the Repair your computer link at the bottom of the window.

Advanced Startup Options will start, almost immediately.
Method 5: Boot From a Windows 8 Recovery Drive

Insert your Windows 8 Recovery Drive into a free USB port.

Tip: Don't worry if you weren't proactive and never got around to creating a Recovery Drive. If you have another computer with Windows 8, or a friend with Windows 8 on his or her computer, see How To Create a Windows 8 Recovery Drive for instructions.

Boot your computer from the flash drive.

On the Choose your keyboard layout screen, tap or click on US or whatever keyboard layout you'd like to use.

Advanced Startup Options will begin instantly.
Method 6: Boot Directly to Advanced Startup Options

Start or restart your computer or device.

Choose the boot option for System Recovery, Advanced Startup, Recovery, etc.

Note: What this boot option is called is configurable by your hardware maker so the options I mentioned are just some that I've seen or heard. Whatever the name, it should be clear that what you're about to do is boot to Windows 8's advanced recovery features.

Important: The ability to boot directly to Advanced Startup Options isn't one that's available with a traditional BIOS. Your computer will need to support UEFI and then also be configured properly to boot directly to the ASO menu.

Wait for Advanced Startup Options to begin.
What About F8 and SHIFT+F8?

Neither F8 nor SHIFT+F8 are reliable options for booting to the Advanced Startup Options menu. See How To Start Windows 8 in Safe Mode for more on this.

If you need to access Advanced Startup Options, you can do so with any of the several methods listed above.

How To Exit Advanced Startup Options

Whenever you're finished using the Advanced Startup Options menu, you can choose Continue to restart your computer, booting you back into Windows 8... assuming it's working properly now.

Your other option is to choose Turn off your PC, which will do just that.

Monday, 24 November 2014

Creating Maintainable WordPress Meta Boxes: Refactoring

Throughout this series, we've focused on building maintainable WordPress meta boxes. By that, I mean that we've been working to create a WordPress plugin that's well-organized, follows WordPress coding standards, and that can be easily adapted and maintained as the project moves forward over time.

Though we've implemented some good practices, there is still room for refactoring. For this series, this is done by design. Whenever you're working on a project for a client or for a larger company, the odds of you having to maintain an existing codebase are rather high. As such, I wanted us to be able to return back to our codebase in order to refine some of the code that we've written.

Note this article will not be written in the format that the others have been written - that is, there won't be a "First we do this, then we do this" approach to development. Instead, we're going to highlight several areas in need of refactoring and then handle them independently of the other changes we're making.

Refactoring

To be clear, the act of refactoring (as defined by Wikipedia) is:

Refactoring improves nonfunctional attributes of the software. Advantages include improved code readability and reduced complexity to improve source code maintainability, and create a more expressive internal architecture or object model to improve extensibility.
In short, it makes the code more readable, less complex, easier to follow, and does so all without changing the behavior of the code from the end-users standpoint.

This can be achieved a number of different ways each of which are unique to the given project. In our case, we're going to look at refactoring our constructors, some of our save methods, some of our helper methods, and more.

Ultimately, the goal is to show some strategies that can be used throughout your future WordPress endeavors. I'll aim to cover as much as possible in this article; however, note that there may be opportunities for additional refactoring that isn't covered.

If that's the case, great! Feel free to make them on your own instance of the codebase. With that said, let's get started.

The Constructor
If you take a look at our constructor:

<?php
        
public function __construct( $name, $version ) {

    $this->name = $name;
    $this->version = $version;

    $this->meta_box = new Authors_Commentary_Meta_Box();

    add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_admin_styles' ) );
    add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_admin_scripts' ) );

}
Notice that it's currently doing two things:

Initializing properties such as the name and the version
Registering hooks with WordPress
It's common practice to see hooks set in the context of a constructor in a WordPress plugin, but it's not really a great place to do it.

A constructor should be used to initialize all properties that are relevant to the given class such that when a user instantiates a class, s/he has everything needed to work with the class.

Since they may not want to register hooks at the time that they initialize the class, we need to abstract this into its own initialize_hooks method. Our code should now look like this:

<?php

public function __construct( $name, $version ) {

    $this->name = $name;
    $this->version = $version;

    $this->meta_box = new Authors_Commentary_Meta_Box();

}

public function initialize_hooks() {
    
    add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_admin_styles' ) );
    add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_admin_scripts' ) );
    
}
After that, we need to make sure to update the core code of authors-commentary.php so that it properly instantiates and registers the hooks.

<?php

function run_author_commentary() {
    
    $author_commentary = new Author_Commentary_Admin( 'author-commentary', '1.0.0' );
    $author_commentary->initialize_hooks();
    
}
run_author_commentary();
Here, the main difference is that we've updated the version number that we're passing to the main class and we're also explicitly calling the initialize_hooks function within the context of run_author_commentary.

If you execute your code right now, everything should work exactly as it did prior to this refactoring.

I'd also like to add that you can make a case for having a separate class responsible for coordinating hooks and callbacks such that the responsibility resides in a separate class. Though I'm a fan of that approach, it's outside the scope of this particular article.

Next, let's go ahead and do the same thing to class-authors-commentary-meta-box.php. Rather than creating a new function, we can simply rename the constructor since the constructor doesn't really do anything. This means our code should go from looking like this:

<?php

public function __construct() {

    add_action( 'add_meta_boxes', array( $this, 'add_meta_box' ) );
    add_action( 'save_post', array( $this, 'save_post' ) );

}
To this:

<?php

public function initialize_hooks() {

    add_action( 'add_meta_boxes', array( $this, 'add_meta_box' ) );
    add_action( 'save_post', array( $this, 'save_post' ) );

}
And the final change that we need to make is to update the constructor in the main class so that it now reads inside of the initialize_hooks function that we created in the main plugin class.

<?php

public function initialize_hooks() {

    $this->meta_box->initialize_hooks();

    add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_admin_styles' ) );
    add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_admin_scripts' ) );

}
Again, refresh the page and your plugin should still be functioning exactly as it were prior to this refactoring.

Helper Methods
In the Authors_Commentary_Meta_Box class, we have a number of conditionals in the save_post function that are very redundant. When this happens, this usually means that much of the functionality can be abstracted into a helper function and then called from within the function in which they were initially placed.

Let's take a look at the code as it stands right now:

<?php
    
public function save_post( $post_id ) {

    /* If we're not working with a 'post' post type or the user doesn't have permission to save,
     * then we exit the function.
     */
    if ( ! $this->is_valid_post_type() || ! $this->user_can_save( $post_id, 'authors_commentary_nonce', 'authors_commentary_save' ) ) {
        return;
    }

    // If the 'Drafts' textarea has been populated, then we sanitize the information.
    if ( ! empty( $_POST['authors-commentary-drafts'] ) ) {

        // We'll remove all white space, HTML tags, and encode the information to be saved
        $drafts = trim( $_POST['authors-commentary-drafts'] );
        $drafts = esc_textarea( strip_tags( $drafts ) );

        update_post_meta( $post_id, 'authors-commentary-drafts', $drafts );

    } else {

        if ( '' !== get_post_meta( $post_id, 'authors-commentary-drafts', true ) ) {
            delete_post_meta( $post_id, 'authors-commentary-drafts' );
        }

    }

    // If the 'Resources' inputs exist, iterate through them and sanitize them
    if ( ! empty( $_POST['authors-commentary-resources'] ) ) {

        $resources = $_POST['authors-commentary-resources'];
        $sanitized_resources = array();
        foreach ( $resources as $resource ) {

            $resource = esc_url( strip_tags( $resource ) );
            if ( ! empty( $resource ) ) {
                $sanitized_resources[] = $resource;
            }

        }

        update_post_meta( $post_id, 'authors-commentary-resources', $sanitized_resources );

    } else {

        if ( '' !== get_post_meta( $post_id, 'authors-commentary-resources', true ) ) {
            delete_post_meta( $post_id, 'authors-commentary-resources' );
        }

    }

    // If there are any values saved in the 'Published' input, save them
    if ( ! empty( $_POST['authors-commentary-comments'] ) ) {
        update_post_meta( $post_id, 'authors-commentary-comments', $_POST['authors-commentary-comments'] );
    } else {

        if ( '' !== get_post_meta( $post_id, 'authors-commentary-comments', true ) ) {
            delete_post_meta( $post_id, 'authors-commentary-comments' );
        }

    }

}
Aside from the method being far too long to begin with, there are a number of things that we can clean up:

The initial conditional that uses logical not and logical OR operators
The conditionals that check the presence of information in the $_POST array
The sanitization, update, and/or delete functions for the associated meta data
So let's take a look at each of these individually and work on refactoring this function.

1. The Initial Condition

The purpose of the first conditional check is to make sure that the current user has the ability to save data to the given post. Right now, we're literally checking to see if the current post type is a valid post type and if the user has permission to save given the current nonce values being passed by WordPress.

Right now, the code reads:

If this is not a valid post type or the user doesn't have permission to save, then exit this function.
It's not all together terrible, but could definitely be improved. Instead of having an OR, let's consolidate it into a single evaluation such that it reads:

If the user doesn't have permission to save, then exit this function.
Luckily, this is a relatively easy fix. Since the type of post that's being save helps to dictate whether or not the user has permission the save the post, we can move that logic into the user_can_save function.

So let's take the is_valid_post_type function and move it into the user_can_save function:

<?php

private function user_can_save( $post_id, $nonce_action, $nonce_id ) {

    $is_autosave = wp_is_post_autosave( $post_id );
    $is_revision = wp_is_post_revision( $post_id );
    $is_valid_nonce = ( isset( $_POST[ $nonce_action ] ) && wp_verify_nonce( $_POST[ $nonce_action ], $nonce_id ) );

    // Return true if the user is able to save; otherwise, false.
    return ! ( $is_autosave || $is_revision ) && $this->is_valid_post_type() && $is_valid_nonce;

}
Now all of the logic that's responsible for determining if the user can save the post meta data is encapsulated within a function specifically designed to evaluate exactly that.

We started with this:

<?php
    
if ( ! $this->is_valid_post_type() || ! $this->user_can_save( $post_id, 'authors_commentary_nonce', 'authors_commentary_save' ) ) {
    return;
}
And now we have this:

<?php
    
if ( ! $this->user_can_save( $post_id, 'authors_commentary_nonce', 'authors_commentary_save' ) ) {
    return;
}
Reads much easier, doesn't it?

2. Checking The $_POST Array

Next up, before we begin sanitizing, validating, and saving (or deleting) the meta data, we're checking the $_POST collection to make sure that the data actually exists.

We can write a small helper function that will take care of this evaluation for us. Though we're essentially writing a little bit of code that makes our evaluation more verbose, the conditionals will read a bit clearer than if we'd just left them as-is.

First, introduce the following function (and note that it takes in a parameter):

<?php

/**
* Determines whether or not a value exists in the $_POST collection
* identified by the specified key.
*
* @since   1.0.0
*
* @param   string    $key    The key of the value in the $_POST collection.
* @return  bool              True if the value exists; otherwise, false.
*/
private function value_exists( $key ) {
    return ! empty( $_POST[ $key ] );
}
Next, refactor all of the calls that were initially calling the ! empty( $_POST[ ... ] ) so that they take advantage of this function.

For example, the function calls should look like this:

if ( $this->value_exists( 'authors-commentary-comments' ) ) {
    // ...
} else {
    // ...
}
2. Deleting Meta Data

Notice that throughout the conditionals that are placed in that function, every evaluating for deleting post meta data if the value does not exist looks the exact same.

For example, we see something like this every time:

<?php

if ( '' !== get_post_meta( $post_id, 'authors-commentary-comments', true ) ) {
    delete_post_meta( $post_id, 'authors-commentary-comments' );
}
This is an obvious chance to refactor the code. As such, let's create a new function called delete_post_meta and have it encapsulate all of this information:

<?php

/**
* Deletes the specified meta data associated with the specified post ID
* based on the incoming key.
*
* @since    1.0.0
* @access   private
* @param    int    $post_id    The ID of the post containing the meta data
* @param    string $meta_key   The ID of the meta data value
*/
private function delete_post_meta( $post_id, $meta_key ) {
    
    if ( '' !== get_post_meta( $post_id, $meta_key, true ) ) {
        delete_post_meta( $post_id, '$meta_key' );
    }
    
}
Now we can do back and replace all of the else conditional evaluations to make a call to this single function so that it reads something like the following:

<?php
    
// If the 'Drafts' textarea has been populated, then we sanitize the information.
if ( $this->value_exists( 'authirs-commentary-drafts' ) ) {

    // We'll remove all white space, HTML tags, and encode the information to be saved
    $drafts = trim( $_POST['authors-commentary-drafts'] );
    $drafts = esc_textarea( strip_tags( $drafts ) );

    update_post_meta( $post_id, 'authors-commentary-drafts', $drafts );

} else {
       $this->delete_post_meta( $post_id, 'authors-commentary-drafts' );
}
At this point, we really only have one other aspect of this part of the code to refactor.

3. Sanitization and Saving

Right now, the way in which the post meta data is saved is done so through a process of evaluating the presence of the data in the $_POST collection, sanitizing it based on the type of information, and then saving it to the post meta data.

Ideally, we'd like to sanitize the data in its own function as well as save the post meta data in its own function. Thus, we need to introduce to new functions.

First, let's work on sanitization. Because we're dealing with textareas and arrays, there are a couple of ways in which we need to handle the sanitization call. Since we're either working with an array or we're not, we can create a function that accepts an optional parameter denoting whether or not we're working with an array.

If we are not working with an array, then we'll treat the incoming data as text; otherwise, we'll treat it as an array:

<?php
    
/**
* Sanitizes the data in the $_POST collection identified by the specified key
* based on whether or not the data is text or is an array.
*
* @since    1.0.0
* @access   private
* @param    string        $key                      The key used to retrieve the data from the $_POST collection.
* @param    bool          $is_array    Optional.    True if the incoming data is an array.
* @return   array|string                            The sanitized data.
*/
private function sanitize_data( $key, $is_array = false ) {

    $sanitized_data = null;

    if ( $is_array ) {

        $resources = $_POST[ $key ];
        $sanitized_data = array();

        foreach ( $resources as $resource ) {

            $resource = esc_url( strip_tags( $resource ) );
            if ( ! empty( $resource ) ) {
                $sanitized_data[] = $resource;
            }

        }

    } else {

        $sanitized_data = '';
        $sanitized_data = trim( $_POST[ $key ] );
        $sanitized_data = esc_textarea( strip_tags( $sanitized_data ) );

    }

    return $sanitized_data;

}
Next, we can update the sanitization calls to use this method. But before we do that, let's also write a small helper that will be responsible for updating the post meta data with the sanitized inputs:

<?php

private function update_post_meta( $post_id, $meta_key, $meta_value ) {
    
    if ( is_array( $_POST[ $meta_key ] ) ) {
        $meta_value = array_filter( $_POST[ $meta_key ] );
    }

    update_post_meta( $post_id, $meta_key, $meta_value );
}
Now we can update all of the conditionals that we were using earlier in the function to read like this:

<?php
    
public function save_post( $post_id ) {

    if ( ! $this->user_can_save( $post_id, 'authors_commentary_nonce', 'authors_commentary_save' ) ) {
        return;
    }

    if ( $this->value_exists( 'authors-commentary-drafts' ) ) {

        $this->update_post_meta(
            $post_id,
            'authors-commentary-drafts',
            $this->sanitize_data( 'authors-commentary-drafts' )
        );

    } else {
        $this->delete_post_meta( $post_id, 'authors-commentary-drafts' );
    }

    if ( $this->value_exists( 'authors-commentary-resources' ) ) {

        $this->update_post_meta(
            $post_id,
            'authors-commentary-resources',
            $this->sanitize_data( 'authors-commentary-resources', true )
        );

    } else {
        $this->delete_post_meta( $post_id, 'authors-commentary-resources' );
    }

    if ( $this->value_exists( 'authors-commentary-comments' ) ) {

        $this->update_post_meta(
            $post_id,
            'authors-commentary-comments',
            $_POST['authors-commentary-comments']
        );

    } else {
        $this->delete_post_meta( $post_id, 'authors-commentary-comments' );
    }

}
Note that we could actually refactor this particular even more so there aren't as many conditionals, but for the sake of the length of the article, the length of time, and also trying to introduce some other strategies, this will be left up as an exercise to be done on your own time.

Conclusion

By now, we've completed our plugin. We've written a plugin that introduces a meta box for providing options for the authors who are writing blog posts.

Additionally, we've employed the WordPress coding standards, some strong file-organization strategies, and have created a number of helper methods and abstractions that will help us to maintain this particular plugin as it undergoes future development.

Because it's not easy to highlight every single opportunity for refactoring, there are likely additional changes that could be made. On your own time, feel free to try implementing some of them on your own.

Overall, I hope you've enjoyed the series and learned a lot from it, and I hope that it will help you to write better, more maintainable code in future WordPress-based projects.