Chapter 10: TwiTorial: A Twitter Application

In This Chapter

• Using the Twitter integration components

• Creating custom colors in App Inventor

• Using the Notifier component as a screen space-saver

Twitter has been at the cutting edge of the social media revolution ever since the company started. The micro blog enabling users to send 140-character messages to the world has become an integral part of the Internet presences of people and corporations alike.

App Inventor includes a Twitter component that has many features required to create your own complete Twitter application. The App Inventor Twitter component has its limitations, which I note as you move through this project.

The value of this project is not just in putting together a Twitter application, but also in exploring how Twitter can be integrated into other applications. You should consider social network integration in many types and categories of applications. Posting statuses or updates to a Twitter feed can be an excellent way to create brand exposure. Status updates can also be used as triggers for your applications. For instance, your App Inventor application can be monitoring a Twitter account for a certain text string as a trigger event.

Creating the TwiTorial Application

The TwiTorial application is quite complex. In terms of number of events and processes, it may be one of the most complex in this book. The instructions for TwiTorial exclusively use typeblocking to create blocks in the Blocks Editor. Because of the sheer number of events and user interactions, I show you a couple of new tricks for maximizing your user interface space and create pleasing design elements. Here are some of the things I cover in this chapter:

• Using the Twitter components

• Truncating very long lists

• Using procedure with result as a text formatter

• Using dynamically sized arrangements to maximize the screen area

• Using a Notifier component as a text input mechanism

• Setting custom Android colors with numbers

Your design

The TwiTorial design specifications contain three screens, as shown in Figure 10-1. A lot goes on with a Twitter application, so you need to use some clever tricks to maximize your screen real estate and make sure the busy interface is pleasing.

Figure 10-1: Your design sketches

9781119991335-fg1001.tif

Your primitives

These are the basic building blocks of functionality that will be required to meet your design goals:

• Buttons/events for requesting timelines (streams of collected messages in chronological order), direct messages (DMs), mentions, and followers (those who choose to receive your tweets)

• Method for formatting for display any list returned by the Twitter component

• Buttons/events/methods for viewing, following, and unfollowing

• Method for creating single color dividing visual elements

• Method for setting custom colors

• Method for truncating extremely long lists

• Method for accepting input from user without wasting screen space for text boxes

New components

This is the primary new component for the TwiTorial project.

• Twitter component

New blocks

These are the new blocks you will be using for the project:

• Length of list

• Add items to list

A lot of primitive concepts and basic capabilities that you use for this application have already been covered in earlier chapters. The preceding list includes only new or unique primitives: A complete list of primitives would probably be three times as long.

Your progression

There is a lot going on in the TwiTorial application. The following logical steps will help you build the primitives up in a fairly progressive way:

1. Set up the user interface elements for VirtualScreen1.

a. Place the Timeline label and display elements.

b. Place the Status, Message, and Followers buttons.

2. Set up the user interface elements for VirtualScreen2.

a. Place the Followers label and display elements.

b. Place Back, Follow, and Unfollow buttons.

3. Place the VirtualScreen3 user interface elements.

a. Place the Direct Messages and Mentions labels and display elements.

b. Place the DM, Refresh, and Back buttons.

4. Place the non-visual components:

a. Three notifiers: TinyDB, Clock, and Twitter components.

5. Set up .Initialize with authorization and formatting logic.

6. Set up the timeline polling.

7. Set up the timeline received logic.

8. Build procedures for formatting incoming lists from the Twitter API.

9. Build status update button event using a Notifier component.

10. Set the DMs and Mentions button event logic.

11. Handle the DMs received event.

12. Handle the Mentions received event.

13. Set up the Followers button event.

14. Handle the Followers received event.

15. Handle the Followers Back button event.

16. Handle the Follow Tweep button event.

17. Handle the Unfollow Tweep button event.

18. Handle the DM Send button event.

19. Handle the Refresh DMs and Mentions button events.

20. Handle the DM and Mentions Back button event.

Warning.eps

As of this writing, the direct message functionality of the Twitter component is not working, but Google is working on a fix that may be done by the time this book is available. I show you how to build the Direct Message functionality and disable it. When Google releases the fix, you can reactivate the blocks for the Direct Message functionality.

Getting Started on TwiTorial

Start a new application project and name it TwiTorial.

1. Make sure the Scrollable property for Screen1 is checked. Lots of information can come in via Twitter and your user may need to be able to scroll the Android screen.

2. Upload the icon from the Chapter 10 project files and set the Icon property.

3. Set the Title property to TwiTorial. You set this property here, although it changes as soon as a user authenticates with the Twitter application programming interface (API). The Title property shows not only the title of the application but the user name who is currently authenticated.

Note.eps

The Twitter API is the command’s returned data that Twitter exposes from their servers to allow developers to create Twitter applications. All of the Twitter API programming has been done for you with the App Inventor Twitter component. When you use the Twitter component, all of the blocks, methods, and function calls send commands to the Twitter servers via the Twitter API.

The TwiTorial project is long enough that you may want to create checkpoints along the way. Refer back to Chapter 1 for a refresher on using the Checkpoints as version control.

Start by building up the user interface elements. The TwiTorial application has three screens. The first, VirtualScreen1, is the default screen and contains the Twitter follower timeline. The follower timeline is all of the status messages that are recent from the people you have followed. The VirtualScreen1 also provides buttons for updating your status message on Twitter. The update status or tweets are handled, like most of the other Twitter API calls, by built-in component method calls. You call the methods by using events controlled by your buttons.

1. Drag and drop a VerticalArrangement and change its name to VirtualScreen1.

2. Set the Width and Height property to Fill Parent.

Next, place the timeline display labels. These labels indicate to the user that they are looking at the timeline from their friends. Set the size of the font a little smaller than normal to get more on the screen. Be careful not to make it too small to comfortably to view. Check the view on your connected Android device.

1. Drag and drop a label into the VirtualScreen1. Rename the label lblTimelineLabel. This label is static and indicates that the next label is displaying the timeline.

2. Set the Text property to say Timeline from friends:.

3. Drag and drop another label below the previous label. Rename the label lblTime-lineDisplay.

4. Clear the default Text property.

5. Set the Width and Height property of lblTimelineDisplay to Fill Parent.

Now place the navigation elements and buttons in a HorizontalArrangement. You need a button to allow your user to send a tweet and buttons to access VirtualScreen2 and VirutalScreen3, which are the Direct Messages and Followers screens, respectively.

1. Drag and drop a horizontal arrangement below the display label.

2. Set the Width property to Fill Parent.

3. Drag and drop a button into the HorizontalArrangement. Rename it btnUpdate-Status.

4. Change the Text property to Update Status. Set the FontSize property to 12.0 pixels.

5. Drag and drop another button to the right of the previous button. Rename the button btnMessages.

6. Change the Text to DMs/Mentions and change the FontSize property to 12.0 pixels.

7. Drag and drop another button to the right of the previous button. Rename the button btnFollowers.

8. Change the Text to Followers. Change the FontSize property to 12.0 pixels.

The timeline display label is populated by the .TimelineReceived event that is generated after a request for the timeline. The timeline consists of status updates from all the tweeps you follow on Twitter in chronological order. (Tweeps are people who use Twitter. I think it’s is a conflation of Twitter and peeps, but don’t hold me to it.) When the application initializes and the authorization is completed, the Clock timer is enabled and the timeline is regularly refreshed with the request for the timeline.

Next set up the VirtualScreen2, which is the screen where you display followers and allow your user to follow and unfollow tweeps:

1. Drag and drop a VerticalArrangement below VirtualScreen1 and rename the VerticalArrangement VirtualScreen2.

2. Set the Width and Height property to Fill Parent.

3. Drag and drop a Label into the VirtualScreen2 and rename it lblFollowerLabel. Set the Text property to Followers:.

4. Drag and drop another label below the first. Rename it lblFollowersDisplay. Remove the default Text property text.

5. Set the Width and Height property on the second label to Fill Parent.

Use a HorizontalArrangement to hold all the navigation and follower action buttons at the bottom of the followers display:

1. Drag and drop a HorizontalArrangement above the display labels and set its Width property to Fill Parent.

2. Drag and drop a button into the HorizontalArrangement. Rename it btnBack-Followers.

3. Set the Text property to Back.

4. Drag and drop a new button to the right of the previous button and rename it btnFollow.

5. Set the Text to Follow Tweep.

6. Drag and drop a ListPicker to the right of the buttons and rename it lstpkrUnfollow.

7. Set the Text property to Unfollow Tweep.

In the series of steps, you will be building the third VirtualScreen, which is used to display both direct messages and mentions from the Twitter API. You will learn a method to divide the screen with a visual element designed to differentiate between direct messages and mentions. I show you a new method for of maximizing the screen real estate without having to control the sizes of all the elements inside of a VirtualScreen. You place all of your components into a VerticalArrangement that you will call AutoSizeArrangement. Then you use Blocks Editor logic to set the size of the AutoSizeArrangement. This accomplishes the same result as merely setting the VirtualScreen to Fill Parent, with the difference that you can select which parts of the VirtualScreen will be considered free for expansion. In other words, you don’t want the entire VirtualScreen to expand out to accommodate the incoming messages and mentions — this would push the navigation buttons well below the visible screen. This would force your user scroll to the bottom of all the incoming messages to reach the navigation buttons. Instead, you want just the labels displaying the incoming data to actually expand to maximum size.

Tip.eps

This is a little bit of an academic exercise, but it teaches you how to make a dynamic arrangement that is not dependent on all of your elements expanding to fill the screen. When you’re designing for larger than average screen sizes such as tablets, this can be even more useful.

The method you use sets the AutoSizeArrangement to be as tall as all of the available Screen1 size, less the size of the HorizontalArrangement holding the navigation elements. The algorithm for making dynamically sized elements is to use Width and Height properties blocks to set the size, using a minus block to remove the size of elements you wish to exclude. You will build the blocks later. For now, just place the required component pieces:

1. Drag and drop a new VerticalArrangement below the existing virtual screens. Rename it VirtualScreen3.

2. Set the Height and Width properties to Fill Parent.

3. Drag and drop another VerticalArrangement into the VirtualScreen3. Rename it AutoSizeArrangement.

4. Drag and drop a label into the AutoSizeArrangement and rename lblDMLabel.

5. Set the Text property to Messages:.

6. Drag and drop a Label component beneath the previous label and rename it lbl-DMDisplay.

7. Remove the default text.

Now you use a clever trick to create a visible element similar to HTML horizontal lines or bars that are used to build web page design elements. Use a horizontally expanding Label with its background color set to black and its Height property statically defined. This creates a horizontal line separating the direct messages from the mentions.

1. Drag and drop a label into the AutoSizeArrangement and rename it lineLabel1.

2. Remove the default text.

3. Set the BackgroundColor to Black.

4. Set the Width property to Fill Parent.

5. Set the Height property to 5 pixels.

This creates a horizontal line 5 pixels high that expands to fill the AutoSizeArrangement and separates the direct messages and mentions. Now place your mentions display elements and the navigation elements below the separator line.

1. Drag and drop a Label component below the horizontal line and rename it lbl-MentionsLabel.

2. Change the Text property to Mentions.

3. Drag and drop another Label component below the previous label and rename it lblMentionsDisplay.

4. Remove the default text.

Now place a HorizontalArrangement in the VirtualScreen3 below the AutoSizeArrangement:

1. Drag and drop a HorizontalArrangement below the AutoSizeArrangement.

2. Drag and drop a ListPicker into the HorizontalArrangement. Rename it lstpkrSendDM.

3. Change the Text property to DM and the FontSize to 10.

4. Drag and drop a Button component to the right of the ListPicker. Rename the button btnRefreshDM.

5. Set the Text property to Refresh DMs and the FontSize to 10.

6. Drag and drop another Button component to the right of the previous button. Rename it btnRefreshMentions.

7. Change the Text property to Refresh Mentions and the FontSize to 10.

8. Drag and drop another button to the right of the previous button. Rename it btnBackDM.

9. Set the Text property to Back and the FontSize to 10.

All of the visible user interface elements should be in place at this point. Now place the nonvisible components. The TwiTorial application makes use of multiple Notifier components for its text entry pop-up. The app also uses the Clock component, the TinyDB component, and, of course, the Twitter component.

1. Drag and drop a Clock component to the Viewer.

2. Drag and drop three Notifier components.

3. Drag and drop a TinyDB component.

4. Drag and drop the Twitter component from the Social palette.

Twitter uses OAuth for communication with its API. OAuth stands for Open Authorization, a standard for authorizing and authenticating applications and users across the Internet. You can read more about OAuth at the OAuth Web site at ouath.net. Because Twitter requires that all third party applications use OAuth to use the API, your application must be authenticated with their system before it can be used. When a user first fires up your application, it asks the user to authorize your application to access their Twitter account via the Twitter API.

There are two parts of the OAuth transaction. First, your application has to be authenticated with Twitter by you, the developer. That’s what the Consumer Key and Consumer Secret you get a little later are for. Second, your user needs to authorize the application to be used with their account. They do this by entering their username and password at the Twitter Web site when they are prompted by your application.

For this to work, you need to register your application with the Twitter OAuth mechanism. The process is fairly easy, but requires some attention to detail. The end result of registering your application is two pieces of information that you must plug into the Twitter component: the Consumer Key and Consumer Secret. Follow the steps below to get your key and secret.

1. Log into your Twitter account or the account that will represent your company, application, and so on. The account doesn’t have to be your personal one but should be an account that will have the information that Twitter and possible users need to contact you.

2. Navigate your browser to http://twitter.com/oauth_clients/new.

3. Fill out the following fields on the New Clients form:

a. Application Name: This must be a unique name for your application. You can’t name the application TwiTorial because I’ve already used that name. You might use something like “Jason’s TwiTorial” instead. The name you choose is what the user sees when they are asked to verify that they want your application to access their Twitter account. In this case, it asks the user if they want the Jason’s TwiTorial application to have access to their account.

b. Description: Enter text here to indicate what your application does to any user that is authenticating. Such as “The TwiTorial application is a simple Twitter client that is used to demonstrate the Twitter API integration with App Inventor.”

c. Application Web Site: This is a required field. This is the URL of a Web site where your users can access more information about your application. If you don’t have such a Web site, enter the URL for your home Web site or some other Web site. This field can’t be left blank.

d. Application Type: Set this to Browser.

e. Callback URL: This must be a valid URL; however, it doesn’t matter what URL you put here because the App Inventor Twitter component populates the correct value here. Just use the same URL you used for the Application Web site field. For developers creating Web or desktop integration, this is the return URL after the user authorizes.

f. Default Access Type: Set this to the Read/Write option.

You can leave the other fields blank.

Make sure you fill out the CAPTCHA at that bottom of the form — you know, the stretched-out twisted series of numbers and letters. The CAPTCHA is to make sure that you are a human filling out the form and not a robot.

4. When your application is registered, you see a page that displays your Consumer Secret and Consumer Key. Write these down and transfer them to the appropriate Consumer-Key and ConsumerSecret properties of the App Inventor Twitter component.

5. From the Design view of your TwiTorial project, click the Twitter component to make it active.

6. In the Properties column, copy the Consumer Key and Consumer Secret to the appropriately labeled property fields.

Your TwiTorial user interface should look like the one in Figure 10-2. Take special note of the dark horizontal line on VirtualScreen3 and the Consumer Key and Consumer Secret in the Twitter component properties.

Now on to building the logic and flow of your Twitter client. Try to keep in mind that this project is more to familiarize yourself with the options available for Twitter integration than it is to make yet another Twitter client. Many Android Twitter clients already do an incredible job. But is there an application that tweets the score and schedule of your PeeWee football league to all the parents? There can be, with the Twitter component and App Inventor.

Begin your Blocks Editor work by setting up the Screen1.Intialize event handler. The .Initialize event has quite a bit to do in the TwiTorial Application. It sets the color of the Screen1.Background to an appropriate Twitter blue. You are familiar by this point with the preset color blocks available in the Colors drawer on the Built-In tab of the Blocks Editor. However, those are all primary and rather non-nuanced colors. Android is capable of displaying millions of colors and App Inventor is capable of using them. All colors in App Inventor are set using numbers that indicate the channel value of the RGBA. The maximum value of each channel is 255. For the R or Red channel, a setting of 255 indicates maximum red. The same is true of all the channels: Red, Green, Blue, and Alpha.

Figure 10-2: The completed TwiTorial user interface

9781119991335-fg1002.tif

Note.eps

You can read more about Android colors on the Android Developer Web site. Learn how to find the right number for the color you want at some of the App Inventor color mixing Web sites listed in the App Inventor Resources site at sites.google.com/site/appinventorresources/home/tutorial-topics/colors.

Use a custom number value to set the color of the Screen1 background to be a light blue color:

1. Typeblock the Screen1.Initialize event handler.

2. Typeblock the Screen1.BackgroundColor [to] block and snap it into the event handler.

3. Typeblock a number block with the number -7164945.0 and snap it into the .BackgroundColor block. You have to type the numbers first and then add the negative sign after the numbers are in the number block.

Note.eps

To test the color with your device attached, right click the Screen1.BackgroundColor block and click the Do It button. Your attached device’s background color should turn the desired Twitter blue. A number, when plugged into a set color block, is interpreted as a color value.

The Screen1.Initialize event also has the logic for the AutoSizeArrangement in VirtualScreen1. You set the Height property of the AutoSizeArrangement to the Screen1 height minus the height of the HorizontalArrangement holding the buttons and navigation elements on VirtualScreen3.

1. Typeblock the AutoSizeArrangement.Height [to] block and snap it in below the .BackgroundColor block.

2. Typeblock a minus operation block and snap it into the .Height block.

3. Typeblock the Screen1.Height block and snap it into the first socket on the minus operation block.

4. Typeblock the HorizontalArrangement3.Height block and snap it into the second socket on the minus operation block.

Note.eps

The HorizontalArrangement you are using as a reference point should be the HorizontalArrangement that contains your buttons on the VirtualScreen3. VirtualScreen3 should be your DM and Mentions screen if you created them in the order indicated previously.

These blocks then set the AutoSizeArrangement to maximize the screen space regardless of the screen size.

Twitter uses OAuth and you should have populated the Consumer Secret and Consumer Key in the Properties column in the Design view. Here I show you how to test to see whether any information is stored in TinyDB that would indicate that a user has previously authorized the TwiTorial application. If the user has previously started your application, they would have been prompted to enter their user name and password that process will authorize your application. If you find a token indicating authorization, your application loads that into a variable so it can be tested to see if authorization is current:

1. Define a variable and set its name to varIsAuth. Plug a blank text block into it.

Your first set of blocks tests whether the TinyDB is empty. If it is not, it loads the contents of the TinyDB into a variable.

2. Typeblock an If block and snap it in below the AutoSizeArrangement in the Screen1.Initialize event handler.

3. Typeblock a not block and snap it into the test socket on the If block.

4. Typeblock an equals comparison operator and snap it into the not block.

5. Typeblock a TinyDB1.GetValue block and snap it into the first socket on the equals comparison operator.

6. Typeblock a text block and replace the default text with isauth. Snap it into the .GetValue block.

7. Typeblock a text block and remove the default text. Snap it into the second socket on the equals operator (=).

These blocks ask the question “Does the database contain a null value? If not, execute the following blocks.”

1. Typeblock the varIsAuth [to] block and snap it into the If block.

2. Typeblock a TinyDB1.GetValue block and snap it into the varIsAuth block.

3. Typeblock a text block and replace the default text with isauth.

These blocks then load the contents stored under the isauth tag into the varIsAuth variable. If you attempt to load a null value from the database into a variable, you get an error that crashes the application. Although it may seem that you sometimes initialize a variable with a nothing or null value through these projects, a blank text block is a zero-length string and not a null value. In traditional programming, a zero-length string is frequently used as a placeholder for later data. You can think of it as a zero-length string being an empty CD but a null value being the absence of a CD.

Next, test the variable to see if it contains a true token to indicate that the application has been authorized. If it has, the application should enable the Clock1.Timer. If there is no true token, the Authorize method call needs to be called.

1. Typeblock an IfElse block and snap it into the .Initialize event handler under the If block.

2. Typeblock the varIsAuth block and snap it into the test socket on the IfElse block.

Note.eps

You can use these kinds of tests if the contents of the variable is a true or false value.

If the variable is true, your app knows that the application has been authorized before and can get on with the business of being a Twitter client:

1. Typeblock the Clock1.TimerEnabled [to] and snap it into the IfElse block.

2. Typeblock a true block and snap it into the .TimerEnabled block.

3. Typeblock the Twitter1.RequestFollowers block and snap it in below the .TimerEnabled block. This requests the followers from the Twitter API, but you have to handle the actual data with the .FollowersReceived event handler.

4. Typeblock the Screen1.Title [to] block and snap it in below the Twitter1.RequestFollowers.

5. Typeblock a make text block and snap it into the .Title block.

6. Typeblock a text block and change the text to TwiTorial, Logged in as:. Make sure to leave a trailing space after the text.

7. Snap the text block into the text socket on the make text block.

8. Typeblock the Twitter1.Username block and snap it into the next text socket on the make text block. This block reports the user name of the authorized user. Thus the Title of Screen1 is changed to TwiTorial, Logged in as: Jwtyler, or whatever user name is authorized on the device.

9. Typeblock the Twitter1.RequestFriendTimeline and snap it in under the Screen1 title block. This requests the status updates of your followed tweeps. The data is returned from the Twitter API and handled with the Twitter1.FriendTimelineReceived event handler.

If the varIsAuth indicates that the device has been authorized previously, the timer is enabled and a request for followers is sent. The Screen1.Title is set to indicate the authorized user.

If the varIsAuth does not contain true, the else-do socket is called, which in turn calls the authorization call from the Twitter component.

Typeblock the Twitter1.Authorize block and snap it into the else-do socket on the IfElse block.

Your completed Screen1.Initialize blocks should look like those in Figure 10-3.

Figure 10-3: The completed Screen1.Initialize blocks

9781119991335-fg1003.tif

The .Authorize block calls the Twitter OAuth Web site, where the user enters their username and password to authorize your Twitter client. The authorization token is then recorded for your client.

When the .Authorize method is called and your client successfully authorizes, the .IsAuthorized event is generated. You use this event to record a true value to the TinyDB and the varIAuth. The .IsAuthorized event handler is also generated when you call the .CheckAuthorization method.

1. Typeblock the Twitter1.IsAuthorized event handler.

2. Typeblock the varIsAuth [to] block and snap it into the event handler. Snap a true block into the to socket.

3. Typeblock a TinyDB1.StoreValue block and snap it in next in the event handler.

4. Typeblock a text block and change the text to isauth. Snap it into the tag socket on the .StoreValue block.

5. Typeblock a text block and change the text to true. Snap the true block into the valueToStore socket on the .StoreValue block.

6. Typeblock the Twitter1.RequestFriendTimeline and snap it in the event handler under the .StoreValue block. This requests the status timeline after the user has been authorized by entering their username and password.

The Clock1.Timer component is the engine that keeps your Twitter client up-to-date. It is relatively simple, calling the .RequestFriendTimeline every few minutes.

1. Typeblock the Clock1.Timer event handler. Make sure the TimerInterval property is set to 120000 milliseconds in the Properties column of the Design view.

2. Typeblock the Twitter1.RequestFriendTimeline block and snap it into the event handler.

You have called both the timeline and followers data from the Twitter API, and now you need to handle the returning data events. However, for both of those events, you build a procedure to handle data returning from Twitter that is formatted as a list by the App Inventor Twitter component. This is very useful when you need to display data that comes in from Twitter. Almost all returned data from the Twitter API is a list. You save yourself lots of work by creating a subroutine that handles any inputted list and returns formatted data:

1. Typeblock a variable and rename it varFormattedList.Snap in a blank text block.

2. Typeblock a new procedure with result and rename it procFormatAnyList.

3. Typeblock a name block and rename it List. Snap the name block into the arg socket on the procFormatAnyList.

4. Typeblock the varFormattedList global variable block and snap it into the return socket at the bottom of the procedure.

Clear out the temporary formatting variable in preparation for formatting the incoming data passed to the procedure:

1. Typeblock the varFormattedList [to] block and snap it into the procFormatAnyList.

2. Typeblock a text block and sets its contents as blank. Snap it into the varFormattedList block.

Next use a ForEach block to format whatever list is passed to the procedure. Your ForEach block formats the text and writes it to the varFormattedList variable. When the ForEach has processed everything in the list, the procFormatAnyList returns the formatted data in the varFormattedList variable. It becomes more apparent how this works when you use it.

1. Typeblock a ForEach block and snap it into the procFormatAnyList.

2. Typeblock the varFormattedList value block and snap it into the list socket at the bottom of the ForEach block.

Note.eps

Make sure that the variable socket on the ForEach has a name block in it with a var name. If you have previously placed ForEach blocks, or you have typeblocked the ForEach, the ForEach variable socket may not populate. If your ForEach block is created without a block in the variable socket, just typeblock a name block and change the name to var#, with the # being a sequential number.

3. Typeblock the varFormattedList [to] block and snap it into the ForEach block.

4. Typeblock a make text block and snap it into the varFormattedList block.

5. Typeblock the varFormattedList global block and snap it into the text socket on the make text block.

6. Typeblock a text block and change the default text to the newline character ( ).

7. Snap the newline character into the next text socket.

8. Typeblock the var value block and snap it into the next text socket.

9. Typeblock a new text block and change it into a newline character. Snap it in the next text socket.

10. Typeblock a text block and change the text to a line of separator characters like this: ----------.

Your completed procFormatAnyList should look like Figure 10-4.

Figure 10-4: The completed procFormatAnyList procedure

9781119991335-fg1004.tif

Now that you have a procedure for formatting incoming lists, you can start handling some of the Twitter components’ received events.

The .FollowersReceived events not only populate the lblFollowersDisplay label, but are also used to populate the two ListPickers you have included in your interface. lstpkrSendDM allows users to select a follower to send a direct message to; lstpkrUnfollow selects a follower to unfollow.

1. Typeblock the Twitter1.FollowersReceived event handler. Notice the followers value that is generated for use in the event.

2. Typeblock the lstpkrSendDM.Elements [to] block and snap it into the event.

3. Typeblock the followers value block and snap it into the .Elements block.

4. Typeblock the lstpkrUnfollow.Elements[to] block and snap it in under the previous ListPicker block.

5. Typeblock another followers value block and snap it into the new .Elements block.

Now you use the procFormatAnyList to format the followers value list and then place that formatted list on the lblFollowersDisplay label.

1. Typeblock the lblFollowersDisplay.Text [to] and snap it in below the ListPicker element blocks.

2. Typeblock the procFormatAnyList call block and snap it into the lblFollowersDisplay.

3. Typeblock the followers value block and snap it into the procFormatAnyList block.

The data returned by the .FollowersReceived event is passed to the procFormat-AnyList procedure and the returned formatted data is displayed in the label.

Your completed .FollowersReceived event should look like Figure 10-5.

Figure 10-5: The completed Twitter1.FollowersReceived blocks

9781119991335-fg1005.tif

You do much the same thing with the Twitter1.FriendTimelineReceived event. However, because the data coming in with that event is likely to be a very long list, you need a method to truncate long lists. Use the Add Items to List block in conjunction with a series of Select List Item blocks to pull only the five most recent status updates from the incoming timeline list. You build a new list held in the varTrimTimeline and then pass that list to the procFormatAnyList to be formatted and then displayed in the timeline display label.

1. Define a new variable and name it varTrimTimeline.

2. Typeblock a make a list block and snap it into the varTrimTimeline variable.

3. Typeblock the Twitter1.FriendTimelineReceived event handler. Make sure there is a name block with the name set to “timeline” in the timeline socket.

First, clear anything in the varTrimTimeline variable from previous trim events:

1. Typeblock the varTrimTimeline [to] block and snap it into the event handler.

2. Typeblock a make a list block and snap it into the varTrimTimeline block.

Note.eps

Never clear a variable defined as a list with a null text value. Doing so causes an error when you attempt to save list items to the variable.

3. Typeblock the lblTimelineDisplay.Text [to] block and snap it into the event handler.

4. Typeblock a Make a List block and snap it into the lblTimelineDisplay.Text block.

Next build an IfElse block that tests to see whether the incoming list is longer than five items. If it is longer than five items, the IfElse calls the truncating blocks in the then-do socket. If not, it just sends the list straight to the procFormatAnyList and then to the display label.

1. Typeblock an IfElse block and snap it in next in the event handler.

2. Typeblock a greater than (>) comparison block and snap it into the text socket on the IfElse block.

3. Typeblock a Length of List block and snap it into the first socket on the comparison operator. The Length of List block returns a number that is the number of items in the list snapped into the list socket.

4. Typeblock the timeline value block from the .FriendTimelineReceived event and snap it into the Length of List block.

5. Typeblock a numeral 5 number block and snap it in the second socket on the comparison operator.

Now build the trimmed timeline to use if the timeline list is longer than five items:

1. Typeblock an Add Items to List block and snap it into the then-do socket on the IfElse block.

2. Typeblock the varTrimTimeline global variable block into the list socket on the Add Items to List block.

3. Now typeblock a Select List Item block and copy it four times so that you have a total of five Select List Item blocks.

4. Plug each Select List Item block in an item socket on the Add Items to List block. It creates a new socket for each one used.

5. Typeblock a timeline value block that is generated when you create the Twitter1.FriendTimelineReceived event. Copy it and paste it five times to create a total of five value timeline blocks.

6. Snap each of the timeline blocks into the list sockets on the Select List Item blocks.

7. Create five number blocks with the numbers one through five on them so that you have 1, 2, 3, 4, and 5 blocks.

8. Snap each of the sequential blocks into the Select List Items blocks’ index sockets. Starting with the number one block in the first Select List Items block, go down through the blocks snapping the next sequential number into the index sockets.

9. Typeblock the lblTimelineDisplay.Text [to] block and snap it in below the Add Items to List blocks.

10. Typeblock the procFormatAnyList procedure call and snap it into the lblTimelineDisplay.Text block.

11. Typeblock the varTrimTimeline global variable block and snap it into the procFormatAnyList procedure call.

Now create the else-do case blocks for the IfElse block. These blocks are called if the incoming list is less than five items. If you attempt to do the trim event on a list smaller than five items, it returns a nasty error and crashes the application:

1. Typeblock the lblTimelineDisplay.Text [to] block and snap it into the else-do socket on the IfElse block.

2. Typeblock the procFormatAnyList procedure call and snap it into the text block.

3. Typeblock the timeline value block and snap it into the procedure list socket.

Your completed .FriendTimelineReceived event handler should look like Figure 10-6.

Figure 10-6: The completed Twitter1.FriendTimelineReceived blocks

9781119991335-fg1006.tif

At this point, you have handled incoming followers and incoming timeline events. You have also handled timeline polling and text formatting. Now you need to start taking care of some of the button events on your user interface. The Update Status button on your VirtualScreen1 is used to send a status update to Twitter. To save screen real estate, you use a Notifier component with a text box pop-up instead of having a text box directly on the user interface. The Notifier component allows your user to input a message into a pop-up text box and then generates an event called .AfterText input. First you call the Notifier component with the button event, and then you handle the .AfterTextInput event for sending the status update.

1. Typeblock the btnUpdateStatus.Click event handler.

2. Typeblock the Notifier1.ShowTextDialog block. This is the block that pops up a text box for input.

3. Typeblock a text block and set its text to Enter Status update <140 characters.

4. Snap the text block into the message socket on the .ShowTextDialog block.

5. Typeblock a text block and change its text to Update Your Twitter status.

6. Snap the text block into the title socket on the .ShowTextDialog block.

Now you need to handle the .AfterTextInput for Notifer1. Twitter status updates can be no more than 140 characters in length, so you need to test the user’s input string to make sure it is within those parameters. You also need to test for a blank text field entry because that will cause an error:

1. Typeblock the Notifier1.AfterTextInput event handler. Make sure the response socket has a name block named response in it.

2. Typeblock an IfElse block and snap it into the event handler.

3. Typeblock an equals (=) comparison operation and snap it into the test socket on the IfElse block.

4. Typeblock the response value block from the .AfterTextInput event and snap it into the length block in the first socket on the comparison operator.

5. Typeblock a text block and set its contents blank.

6. Snap the blank text block into the second socket on the comparison operator.

7. Typeblock the Notifier1.ShowAlert block and snap it into the then-do socket on the IfElse block.

8. Typeblock a text block, set its text to No Status Entered, and snap it into the Notifier1.ShowAlert block.

If the user has entered some text into the text box, you need to test whether it is greater than the maximum 140 character limit and alert the user if it is. You use an IfElse block nested in the else-do socket:

1. Typeblock a second IfElse block and snap it into the else-do socket on the IfElse block already in the .AfterTextInput block.

2. Typeblock a greater than (>) comparison operator and snap it into the test socket of the new IfElse block.

3. Typeblock a length block and snap it in to the first socket on the comparison operator.

4. Typeblock the response value block and snap it into the first socket on the comparison operator.

5. Typeblock a number 140 block and snap it into the second socket on the comparison operator.

6. Typeblock the Notifier1.ShowAlert block and snap it into the then-do socket on the second nested IfElse block.

7. Typeblock a text block and set its text to Status update must be less than 140 characters.

8. Snap the text block into the notice socket on the .ShowAlert block.

9. Typeblock the Twitter1.SetStatus block and snap it into the else-do socket on the nested IfElse block.

10. Typeblock the response value block and snap it into the status socket on the .SetStatus block.

This last nested IfElse block checks to see whether the response from the user in the pop-up dialog box is greater than 140 characters and then appropriately either warns them or sends the status update to Twitter.

Your completed btnUpdateStatus.Click and Notifier1.AfterTextInput blocks should look like Figure 10-7.

The DMs and Messages buttons on the main screen are primarily navigation buttons in that they bring up VirtualScreen3, where the direct messages and mentions are displayed. However, they also make two Twitter API calls to prepare the display labels with content. The .RequestDirectMessages method and .RequestMentions method send a request to Twitter. When Twitter responds with the requested data, an event is generated and it is formatted as a list. You need to handle the btnMessages.Click event and then move on to handling the incoming data when a successful request is made.

Figure 10-7: The completed btnUpdateStatus.Click and Notifier1.AfterTextInput event handlers

9781119991335-fg1007.tif

Note.eps

As mentioned at the beginning of this project, the Twitter Direct Messages functionality is currently broken in App Inventor. However, the issue is likely to be fixed very soon. I show you how to build the functionality and then use App Inventor’s deactivate block function to keep the Direct Message request from being called. When the Google developer team announces a fix at http://groups.google.com/group/app-inventor-announcements, you can reactivate the blocks.

1. Typeblock the btnMessages.Click block.

2. Typeblock the VirtualScreen1.Visible [to] block and snap it into the event handler.

3. Typeblock and snap a false block in the VirtualScreen block.

4. Typeblock the VirtualSceen3.Visible [to], snap it in next, and set it with a true block.

Next make the calls to the Twitter API for the direct messages and mentions:

1. Typeblock the Twitter1.RequestDirectMessages block and snap it in next in the event handler. Right-click the .RequestDirectMessages block and select the Deactivate option from the right-click menu.

Note.eps

Right-clicking any block and selecting Deactivate from the right-click menu prevents the block and any blocks it contains from being executed by your application on your Android device. Deactivated blocks turn white. To re-activate a deactivated block, just right-click and select the Activate option. The Deactivate option is a good troubleshooting tool, too. When you are unsure if an event or series of blocks are causing a bug or issue, deactivate them to see if doing so resolves the issue.

2. Typeblock the Twitter1.RequestMentions block and snap it in next.

Now you need to handle each of the events generated when the direct messages and mentions are returned from Twitter. Thanks to your procFormatAnyList procedure handling, the incoming lists are as simple as passing the incoming data to the procedure and placing the return result into the appropriate display label. Your procFormatAnyList procedure starts to pay off in spades at this point. Handling repetitive tasks with a subroutine like procFormatAnyList really speeds up development:

1. Typeblock the Twitter1.DirectMessagesReceived event handler. Make sure there is a name block snapped into the messages socket with the name set to messages.

2. Typeblock the lblDMdisplay.Text [to] block and snap it into the event handler.

3. Typeblock the procFormatAnyList procedure call and snap it into the text block.

4. Typeblock the messages value block into the List socket on the procFormatAnyList block.

5. Right-click the Twitter1.DirectMessagesReceived event handler and select the Deactivate option from the right-click menu. You can reactivate this event handler when the direct messages issue is resolved by Google.

Thanks to the work being done by your list processing factory, that’s all you have to do. Now do the same for the .MentionsReceived event:

1. Typeblock the Twitter1.MentionsReceived event handler. Make sure a name block is snapped into the mentions socket with the name set to mentions.

2. Typeblock the lblMentionsDisplay.Text [to] block and snap it into the event handler.

3. Typeblock the prodFormatAnyList and snap it into the label block.

4. Typeblock the mentions value block and snap it into the list socket on the procedure call.

The btnMessages.Click, .DirectMessagesReceived, and .MentionsReceived events should look like the ones in Figure 10-8.

Figure 10-8: The btnMessages.Click, .DirectMessagesReceived, and .MentionsReceived completed event handlers

9781119991335-fg1008.tif

Like the DMs and Messages button on VirtualScreen1, the Follower button on VirtualScreen1 is primarily a navigation button. It also sends a request to Twitter for a latest list of followers. As before, you handle the return data from Twitter in a separate event:

1. Typeblock the btnFollowers.Click event handler.

2. Typeblock the VirtualScreen1.Visible [to] block set it with a false block and snap it into the event handler.

3. Typeblock the VirtualScreen2. Visible [to] block, set it with a true block, and snap it into the event handler.

4. Typeblock the Twitter1.RequestFollowers block and snap it into the event handler.

You have already setup the .FollowersReceived event because it was called from the Screen1.Initialize block. You call the .RequestFollowers here to make sure that the locally displayed list is still fresh.

VirtualScreen2 has three buttons: Back, Follow, and Unfollow. The Back button is purely navigational, allowing your user to return to the main screen:

1. Typeblock the btnBackFollowers.Click event handler.

2. Typeblock the VirtualScreen1.Visible [to], snap it into the event handler, and set it with a true block.

3. Typeblock the VirtualScreen2.Visible [to] and snap it into the event handler. Set it with a false block.

The Follow button uses the same Notifier pop-up method we used previously. It allows your user to input a Twitter user’s (or tweep’s) name and follow that person:

1. Typeblock the btnFollow.Click event handler.

2. Typeblock the Notifier2.ShowTextDialog block and snap it into the event handler.

Note.eps

This is the Notifier2 component. You are using separated Notifier components because you need unique .AfterTextInput event handlers.

3. Typeblock a text block, set the text to Enter User Name to Follow, and snap it into the message socket on the Notifier2 block.

4. Typeblock a text block, set the text to Follow Tweep, and snap it into the title socket on the Notifer2 block.

Now you need to handle the event generated by the user entering text in the pop-up dialog box:

1. Typeblock the Notifier2.AfterTextInput block. Make sure there is a name block snapped into the response socket and that it is named response1.

2. Typeblock the Twitter1. Follow block and snap it into the event.

3. Typeblock the response1 block that is generated by the event handler and snap it into the user socket on the Twitter1 block.

The Follow blocks should look like those in Figure 10-9.

Figure 10-9: The completed btnFollow.Click and Notifier1.AfterTextInput blocks

9781119991335-fg1009.tif

The Unfollow button is a ListPicker that is populated by the follower’s returned event. Your logic blocks allow the user to select a user and unfollow them using the ListPicker. Because the elements are already populated, all you need to do is handle the .AfterPicking event to unfollow the selected user:

1. Typeblock the lstpkrUnfollow.AfterPicking event handler.

2. Typeblock the Twitter1.StopFollowing block and snap it into the event handler.

3. Typeblock the lstpkrUnfollow.Selection block and snap it into the user socket on the .StopFollowing block.

VirtualScreen3 has four buttons on it. Refresh DMs and Refresh Mentions are for refreshing the display. Their event handlers access the Twitter component .RequestDirectMessages and .RequestMentions methods. The Direct Message button is for sending a DM to another Twitter user. The Direct Message button uses the same method as you have used previously, except with a ListPicker to populate the user field. Tapping the DM button brings up a list of followers. After a follower is selected, a Notifier dialog box appears with a text box that allows the user to enter a text message. You then handle that text with the .AfterTextInput event. The Back button returns your user to the main screen.

First use the .AfterPicking event to call the notifier:

1. Typeblock the lstpkrSendDM.AfterPicking event handler.

2. Typeblock the Notifier3.ShowTextDialog block.

Note.eps

This is Notifier3. You do not want to create duplicate .AfterTextInput events from a previously used notifier. Duplicate events from the same component cause your application to error out and force close.

3. Typeblock a text block and replace the text with Enter Text for DM. Snap the text block into the message socket.

4. Typeblock a text block and replace the text with Enter Message. Snap it into the title socket.

Now you need to handle the .AfterTextInput event generated when your user enters some text and taps the OK button:

1. Typeblock the Notifier3.AfterTextInput event handler block. Make sure there is a name block snapped into the response socket and that its name is set to response2.

2. Typeblock the Twitter1.DirectMessage block and snap it into the event handler.

3. Typeblock the lstpkrSendDM.Selection block and snap it into the user socket.

4. Typeblock the response2 value block and snap it into the message socket.

Your user taps the DM button and is presented with a list of followers. After the user selects one of the followers, the Notifier dialog box appears with a text field for text entry. The user types their DM text, taps OK, and sends the message to Twitter. Your completed Direct Message events should look like the ones in Figure 10-10.

Figure 10-10: The completed lstpkrUnfollow.AfterPicking and Notifier3.AfterTextInput events

9781119991335-fg1010.tif

The Refresh buttons on VirtualScreen3 are fairly simple. They call the Twitter API to send the mentions and DMs to the device. This, of course, generates the .Received events that you have already handled. The Back button is strictly navigational and takes the user back to the main VirtualScreen1:

1. Typeblock the btnRefreshDM.Click event handler.

2. Typeblock the Twitter1.RequestDirectMessages and snap it in the event handler.

Next, handle the Mentions refresh:

1. Typeblock the btnRefreshMentions.Click event handler.

2. Typeblock the Twitter1.RequestMentions and snap it into the event handler.

The Back button is navigational and takes the user back to VirtualScreen1.

1. Typeblock the btnBackDM.Click event handler.

2. Typeblock the VirtualScreen3.Visible [to] block and snap it into the event handler. Set the block with a false block.

3. Typeblock the VirtualScreen1.Visible [to] and snap it in to the event handler next.

4. Set it with a True block.

With all of your events and all of your design goals met, it’s time to package the TwiTorial application for your phone. If you generate any errors, look back over the figures and double-check your blocks. Refer to Chapter 1 for a refresher on how to package your application.

The TwiTorial application is large and has a lot of events going on. The primary purpose of developing the TwiTorial app is to help you understand the Twitter integration that is possible for App Inventor applications. As I mentioned earlier, you can use Twitter integration in many applications that are not primarily Twitter clients.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.239.76.211