Late last week, we got notice that my pet iPhone project (SnappFiles) got approved for download on the Apple App Store. Yay! We got hundreds of downloads in the first 48 hours and some great feedback so far.
What is this SnappFiles thing? It's a way of accessing your Lotus Quickr files from an iPhone or iPod Touch (or, in a few months, your new iPad). Works with Quickr 8.0 and higher, both the Domino and the Websphere versions. It uses the native iPhone viewers to display files, so any file format the iPhone can natively view can be used to open a Quickr file.
For a general description of what the app does, Rob Novak -- owner and intergalactic leader of SNAPPS, aka "my boss" -- did an excellent overview on the day it was released, and Paul Mooney has a nice writeup with lots of screenshots. I also put a short demo video up on YouTube, if you're a visual learner:
A few common questions we've received in the past several days:
One of the things that took a really long time was getting the 11 minute video of how to create a native iPhone app to an acceptably quality for viewing. The video I played during the session was over 3 GB in size (super high-def to get the best quality on the big screen in the session room). I obviously couldn't and didn't want to upload such a giant video to Vimeo, partially because it was too darn big, and partially because Vimeo was going to scale it down after it was uploaded anyway, so you automatically lose quality. Here are the settings I ended up using:
That produced a 231 MB file, and it looked good enough for me after upload and processing. I'm actually not crazy about the audio quality (too much sibilance, I also have several vocal tics that would have been good to edit out), but after messing with the video settings and waiting 2 hours for each new output file and many more hours for each upload, I finally just called it "done".
First, I'm going to do a writeup of the conference after it's over. There have been some interesting announcements this week -- I'm sure you've read about them on many of the other blogs on PlanetLotus, so it's not like you're missing the whole confence just 'cause I'm not blogging it. However, I was lucky enough to be in the blogger program again this year, which has given me some access to people and information that might make for a few interesting comments when I get to do my writeup.
Second, me and Bruce have recorded two Taking Notes Podcasts already during the conference, and we'll be doing at least one more before we go home. Take a listen to those to hear some of my current thoughts on the conference.
Third, I presented my iPhone development session this morning and there are a couple things to mention as far as that goes:
Finally, speaking of sessions, here are the two sessions I'm giving tomorrow (Thursday):
I think there's a shortcut between Y&B and Dolphin if you go over the parking lot and through the woods, but that's not clear on this picture. You can probably figure it out with a Google satellite map of the Dolphin though.
Session session = getSession();
AgentContext agentContext = session.getAgentContext();
Database db = agentContext.getCurrentDatabase();
lotus.domino.Document doc = db.getAllDocuments().getFirstDocument();
DxlExporter exporter = session.createDxlExporter();
exporter.setOutputDOCTYPE(false); // avoid restricted access errors
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
factory.setValidating(false);
org.w3c.dom.Document domDoc = factory.newDocumentBuilder().parse(
new ByteArrayInputStream( exporter.exportDxl(doc).getBytes() ));
doc.recycle();
When you run this on a Domino server in an agent, the "exporter.setOutputDOCTYPE(false);" line is important. If you do not include that line, your agent will need to have a runtime security level of "2. Allow restricted operations" to avoid getting java.lang.SecurityException and lotus.notes.AgentSecurityManager errors -- and the ID it runs under will need to have unrestricted access on the server. If you do include that line, the agent can run under the standard runtime security of "no restricted operations".
That's my experience on a Domino 8.5.1 server anyway. If this lesson has been covered already, I either didn't see it or had to learn it for myself.
That's the Notes form and the resulting HTML code. I decided to put one of the fields in a Dojo dialog, just to fancy it up a bit (there was actually a better reason than "fancy it up", but that's a good reason for my example here). To do this, I added a little HTML around the field like so:
All was good, you could click a button to display a dialog and enter information into the field, and the world kept spinning 'round. The only problem was, when the web form was actually submitted, there was no data in the field that's in the dialog. If I didn't use a Dojo dialog the field got submitted fine; if the Dojo dialog div surrounds the field, the field data was empty. Weird.
Looking at the HTML above, it all looks good. There are a few extra tags on the page, but nothing that should clear out the field data or anything. I even wrote some JavaScript to make sure that the field data was there after the dialog closed (just in case Dojo misplaced it somehow). Still looked good. Then I looked a little closer with Firebug:
Ah ha! Look at where the form is, and look at where Dojo moved the dialog div. The div is now beneath the form. So the field isn't inside the Form block at all now. So when you submit the form, the field doesn't get submitted because it's no longer a part of the form. If that doesn't make sense, consider the fact that there can be multiple forms on a page, each one submitting only its own fields.
My answer ended up being that I added code to copy the dialog field text to a hidden field that was still inside the form, so the field data still got submitted. There are probably other ways to work around this too. Ultimately, it just showed me that it's essentially impossible to debug web forms without Firebug these days.
Oh, and the same thing will happen if you do this on an XPage too. Dojo is an equal opportunity HTML rearranger.
UPDATE: make sure to check the comments for some other good ways to work around this problem.
This is the third year they're doing the awards, and it's simple to enter. Here's the process:
If you'd like an example of a winning application, Theo Heselmans won last year with a very polished Domino web survey app.
Also, even if you get to the demo stage, you will NOT be asked for source code or intellectual property related to the application, so don't worry about that. Teamstudio is just looking for companies that do interesting things with Notes/Domino because those are people who can really use their tools. And if your company is "shy" about being named in a contest like this, that's okay too (notice that the second place winner in last year's press release requested anonymity).
FULL DISCLOSURE: I am one of the judges for the contest.
It's got Java and LotusScript agents with examples of using CSV, ODBC, XML, JSON, OLE, and Web Services to import and export data. There is also a page with an example of using the Bluff JavaScript graphing library.
I've recently had a few e-mail questions regarding that code, so after 5 years of letting that database gather dust I made some updates to the code to fix the following problems:
If you're interested, download the database and take a look.
It's a round table that expands in a crazy, geometric way when it's rotated around. Here's a video:
It's called a Fletcher Capstan Table, custom built to order by DB Fletcher Design. No prices. If you have to ask, you can't afford it.
And to be clear (just so that's not interpreted as some conniving back-handed compliment) even ignoring the Julian-sleep-scale, I think that UKLUG last week was an incredible show.
Warren and Kitty Elsmore -- probably the most thoughtful people on the entire planet -- headed up the organization of this very well executed event, and I can't begin to imagine how much work it was. From the opening session with Lotus GM Bob Picciano and demo-man Ron Sebastian, to the technical sessions, to the welcome reception Scottish ceilidh, to the closing session where vendors gave away everything from iPods and iPhones and Blackberries to a trip to Nice, it all ran smoothly.
A few personal highlights and comments:
Okay, back to work.
For some reason the cheesy music part of the audio track didn't get converted and the video is still a little fuzzy, but whatever. I didn't even have a YouTube account until a couple hours ago. I'll figure it out someday if it becomes important.
Also, a search for "LotusKnows" on YouTube yields several more videos that might be fun to watch.
It's a little client integration demo: taking a flight reservation, uploading to TripIt, viewing in the TripIt sidebar widget, viewing the ical feed in my Notes calendar, and using Live Text and the embedded browser to look up information and drag or copy it to a new calendar entry. The goal was to show how to do all these things using the out-of-the-box Lotus Notes client and mail template, no customizations required. I think the only extra thing I added was the TripIt widget itself just 'cause I think it looks nice.
I need to get a bigger version of the video on YouTube or somewhere so you can see a little more detail on what I'm doing. You can get the idea from the small version on the Lotus Knows site though.
So, you added a checkbox field to a Domino form and the choices are all jumbled together. How do you line them up so they look nice and neat?
That old chestnut of a problem has been discussed for many years (since there's still no built-in way to do it), and most of the solutions seem to be around using some amount of formula language to rewrite the checkbox choices before they're displayed. See Jake Howlett's checkbox formatting article and the comments below it for some good examples.
I wanted another method for lining up checkbox fields in Domino -- namely, a method that didn't require me to touch the checkbox choices at all. I wanted as unobtrusive an answer as I could find. Here's what I came up with:
The process is:
Here's the JavaScript to format a div with ID of "checkboxFieldDiv1":
function lineUpCheckboxes (div) { if (typeof div === "string") { div = document.getElementById(div); } if (!div) { return; } var cbText = div.innerHTML; // this is for reformatting pre-8.5 checkbox fields to add <label> tags if (cbText && cbText.toLowerCase().indexOf("<label>") < 0) { var arr = cbText.split(/<input/gi); cbText = arr[0]; for (i = 1; i < arr.length; i++) { if ((arr[i].toLowerCase().indexOf('type="checkbox"') >= 0) || (arr[i].toLowerCase().indexOf('type=checkbox') >= 0)) cbText += "<label><input" + arr[i] + "</label>"; else if ((arr[i].toLowerCase().indexOf('type="radio"') >= 0) || (arr[i].toLowerCase().indexOf('type=radio') >= 0)) cbText += "<label><input" + arr[i] + "</label>"; else cbText += "<input" + arr[i]; } } cbText = cbText.replace(/<label>/gi, "<td style='padding:0px'><label>"); cbText = cbText.replace(/<\/label>/gi, "</label></td>"); cbText = cbText.replace(/<p>/gi, ""); cbText = cbText.replace(/<\/p>/gi, ""); var pos = cbText.indexOf("<td"); if (pos >= 0) { cbText = cbText.replace(/<br>/gi, "</tr><tr>"); var tbStart = "<table width='98%'><thead></thead><tbody><tr>"; var tbEnd = "</tr></tbody></table>"; pos = cbText.indexOf("<td"); cbText = cbText.substr(0, pos) + tbStart + cbText.substr(pos) + tbEnd; } div.innerHTML = cbText; } window.onload = function () { // this is a REALLY bad way to add a window.onload event, but I'm trying to keep // it short for the sake of example. Search Google for better ways to do this. lineUpCheckboxes("checkboxFieldDiv1"); };
You can also download the file LineUpCheckboxes.js if you don't feel like copying and pasting.
Over 1/3 of the function code deals with the fact that pre-8.5 Domino servers don't put a <label> tag around checkbox or radio button options, and the rest is some hard-coded string replacements based on how Domino outputs HTML. The really nice thing is, the font face and the number of columns you specify for the field in Domino Designer are still used so there's no extra coding involved there. Since the reformatted fields are in a <div> or your choosing, you can also use all the CSS you want to further refine the look.
I tested this on Domino 7, 8, and 8.5 using Firefox 3/3.5, IE7/8, and Safari. Seemed to work for me. Sadly this does not work with checkbox groups on XPages, so if you're using XPages you're on your own.
I really do wonder, though, if there's not some way to simplify that function. It's only 35 lines of code but it still looks a little tedious to me. If you're a regular expression wizard or if you're really good with the JavaScript toolkits, you might want to try to boil that function down a bit to shorten it up.
Oh, and this works for radio button fields too.