Michael A. Covington    Michael A. Covington
Books by Michael Covington
Consulting Services
Previous months
About this notebook
Search site or Web
Ichthys

Daily Notebook

Popular topics on this page:
Screen updates in WPF, the wrong way and the right way
Has Adobe Photoshop CS2 become freeware?
Jim Mauldin, 1938-2013
1999 Isuzu Rodeo, Honda Passport - Silencing keyless entry and alarm
My position on gun control
Replacing automotive lift struts
Ethical tests for multi-level marketing schemes
Astrophotos:
Moon and Jupiter
Many more...

For more topics, scroll down, press Ctrl-F to search the page, or check previous months.

For the latest version of this page at any time, use this link: www.covingtoninnovations.com/michael/blog



2013
January
31

Some ethical tests for multi-level marketing schemes

[Revised.]

I've blogged about multi-level marketing (MLM) before, and as you probably know, I'm generally quite wary of it.

This could be because I've seen more bad MLMs than good ones simply because only the bad ones make pests of themselves.

Anyhow, here are my thoughts.

MLM is a marketing scheme where, in addition to selling a product, you make money by recruiting more sales reps, and you get a cut of their income, and so does the person who recruited you, and so on, all the way up the tree. If you are near the top of a big tree, you can (reportedly) get rich.

Please note: I do not say that MLM is always wrong. In pre-1900 America, it was almost the only way to reach a wide and thinly scattered population. There may be special situations in which it still works well. Good signs that an MLM might be trustworthy include having a large variety of products, selling some products that are also sold in stores, and above all, not leading new recruits to think they're about to get rich. It's also a good sign if the MLM is a publicly traded company that must report its finances to shareholders.

But please note that there are also illegal Ponzi schemes in the world, some of them claiming to be legitimate MLM. A Ponzi scheme doesn't sell products, only memberships. (Or the sale of products is only a small part of its income.) A Ponzi scheme is doomed to collapse when it runs out of people to recruit, leaving the relatively new recruits with a financial loss. This collapse is a mathematical certainty whether or not you understand it. They're counting on you not to understand it.

Getting back to apparently legitimate MLM, though, here are a number of concerns. Not all of them apply to every MLM company. If you are a person of conscience, please ask yourself carefully whether any of these objections applies to the scheme you're thinking of joining.

(1) Honesty about expectations. Are your own expectations realistic? Are you expected to recruit people by raising unrealistic expectations? (That's wrong.) Do you even have a way to know whether your expectations are realistic? Do you know how much money all the members make, not just a few superstars? Or are you being kept in the dark?

(2) Medical ethics and drug laws. Some of the least trustworthy MLMs sell a single product or a small set of products that are claimed to cure or prevent disease. The United States has strict laws and regulations about the claims that sellers can make about any such product. Otherwise, anybody could claim that anything cures anything.

A worrisome trend I've seen in MLM is recruiting people who aren't medically trained, and getting them to say things, by word of mouth, that are not legal to say in advertising because they aren't backed up by government-recognized scientific evidence. And I mean backed up independent tests, not just the manufacturer's own claims. Please be very careful that you don't get suckered into violating U.S. drug laws in this way.

(3) Quack paranoia. If anybody should happen to say, "The medical establishment doesn't want you to know about this because it will put them out of business," run, don't walk, and get away as fast as you can. That's classic quackery. Every charlatan wants to convince you that all his critics are an evil conspiracy that should be ignored.

(4) The free market. Exactly why is the product "not sold in stores"? Surely the manufacturer wants to sell as much of it as possible. This isn't 1850; it's easy to get products distributed everywhere; so why not do so? Maybe the products actually can't compete on price or quality. It's a question worth asking.

(A possible answer might be that MLM has access to a workforce of people who don't want to work any other way. Unlike other sales jobs, MLM membership can easily be a very part-time activity. I don't know how the economics of this actually works out — but at least I thought of asking the question.)

(5) Economic fairness. Why should everybody above you in the tree get a cut of your income, forever? They aren't doing any work or providing you with anything on an ongoing basis. Many people will become increasingly uneasy with this kind of arrangement as time goes on.

(6) Excessive emotion. When I start asking critical questions — even mild ones — about an MLM scheme, I sometimes get an extremely hostile emotional response, as if I were insulting someone's mother or baby. That's how I know I'm not talking to a normal businessperson. Ordinary businesspeople do not have that kind of emotional loyalty to a venture; they're always skeptical, ready to drop anything that doesn't pan out. Too much emotion means too little logic and real information.

2013
January
30

A word to the wise about tag lines

Many people put a slogan or favorite quotation at the end of all their e-mail. That's called a tag line.

Well... I thought everybody knew this by now, but maybe not...

When you're sending e-mail from work, on behalf of your employer, don't include a tag line that has any chance of seeming offensive. Better yet, don't include a tag line at all. Your employer's business correspondence is not the place to interject your opinions.

Today I received, from a fairly important administrative office, an e-mail decorated with the quote:

"If you want something said, ask a man. If you want something done, ask a woman." — Margaret Thatcher

I'm sure Lady Thatcher (whose political achievements I admire) said this in some context where it was genuinely humorous. But as a tag line on a large institution's official correspondence, it's not appropriate. Out of context, it insults men by saying they are all talk and no action. The policy of this particular institution, thank goodness, is that women and men are equal.

I've seen worse. Years ago, one well-intentioned person tagged everything with "Pray for the unlovable." This led to combinations like, "The Dean has announced budget cuts. Pray for the unlovable."

What about freedom of speech? Simple. Exercise it when speaking for yourself, not when speaking for your employer.

2013
January
29

Replacing automotive lift struts
1999 Isuzu Rodeo, 1999 Honda Passport, many others

A typical automobile today has anywhere from two to six lift struts, holding up things like the tailgate, trunk, or hood. When they get ten years old or so, they lose their strength and fail to hold up their load — first in cold weather, then all the time.

Replacing them is a very quick job. New struts cost about $25 each (you'll need two), and almost all are made by one company, Stabilus.

There are several videos on the Web that describe the procedure — here's one — and they say to use a screwdriver to release the clip. But the videos that I looked at didn't show exactly where to put the screwdriver, so let me reveal the answer:

You can insert the screwdriver from either end. Don't pop the clip all the way off if you're going to reuse the strut. (Destroying the old one is OK.) Just pull the clip back a bit, and the strut will come right off the ball-head bolt to which it is attached. The new strut pops on with moderate hand pressure without any manipulation of the clip.

If you're a gadgeteer, you may want to keep the old struts and use them on something with a lighter load. You'll be surprised at how strong they are, even if they no longer hold up your tailgate window. Stabilus gives you new ball-head bolts, just in case you need them, so you can easily add a strut to something (maybe the lid of a footlocker?) where there wasn't one originally.

2013
January
28

My position on gun control

[Minor revisions Jan. 28 and 29. Italics added Jan. 29.]

My position on gun control is simple: I don't have one. We already have gun control. Whether present laws draw the line in the right place is a question that depends on facts about how guns are acquired and used — facts that I am not master of.

So my position has to be, "I don't know." It is not sufficient just to imagine what I think people do with guns, nor even to reason from a few single examples and incidents. In fact, some people have pointed out, quite rightly, that the current concern with gun control is driven by rare incidents, not common ones. Someone needs to gather information about what is really happening on a large scale. We need to study the thousands of guns that are in every town, and learn how they are used constructively and destructively, and think about how to shift the balance toward constructive use. That's the hard part of making good public policy. You can't do it by mere guesswork.

But I've observed that each side in the gun debate needs to be told some things. Neither side seems to have any idea what's in the minds of people on the other side. So that's what I'll address today.

The anti-gun people fail to understand two things. First, they fail to understand how America has been — and, to an extent that would surprise any European, still is — a sparsely populated place. It used to be common to be 100 miles from the nearest police or sheriff. It is still common to be 10 or 20 miles from them. And we even have places where cell phones don't work.

On the sparsely populated frontier, guns, and especially handguns, were essential, as the "great equalizer," to make it reasonably safe for individuals to move around by themselves. They made it possible to be a cowboy or a rancher, not just a town dweller. In some places and situations, this need is still present.

(Europeans and city dwellers easily fail to realize that wild animals are real. There have been no bears in England for hundreds of years, but we Americans still have them, including grizzly bears that will kill a human at any opportunity. And rural American life includes the need to protect livestock and pets from coyotes and the like.)

The other thing anti-gun people fail to understand — and about which foreigners are incredulous — is that our history and our constitution say we have the moral right to overthrow our government if it becomes oppressive. Not the legal right, of course, because overthrowing it would overthrow its laws. But a unique part of the American worldview is that a violent revolution is the last defense of democracy — indeed, the very possibility of a revolution keeps us from actually having to have one. For that reason, any plan to disarm the whole populace is viewed with suspicion. This is what all that "Second Amendment stuff" is all about. It's something you can't ignore when participating in the American gun control debate.

A couple of foreigners asked me why an "amendment" to the Constitution is so sacrosanct. The answer is that our first 10 amendments are contemporaneous with the Constitution itself; they are our Bill of Rights and were added right at the beginning because of widespread feeling that the original Constitution was incomplete. The Second Amendment is not something that came along as an afterthought decades later.

Now to the pro-gun people. First, a relatively minor point: Gun advocates often talk as if military technology were the same today as in 1776. In reality, individuals with rifles can't stand up to a modern army. The situation foreseen in the Second Amendment is not the situation today. We certainly don't want to allow private ownership of fighter jets or nuclear warheads. Our defense of democracy needs to work differently.

Anyhow, the "well-regulated militia[s]" mentioned in the Second Amendment (and I know "well-regulated" means "well-organized," not "heavily restricted") were foreseen as community efforts. I would argue the framers of the Second Amendment never meant to set up each and every individual as a potential traitor. They were thinking more about local autonomy. If the federal government oppresses a particular region, its inhabitants might rise up collectively.

But I have a much bigger thing to point out to gun advocates: Too many of you talk as if you're fascinated with guns for all the wrong reasons. I know they don't speak for all of you, but entirely too many gun advocates come across as uncooperative, combative, paranoid, and fascinated with having the technology to kill their neighbors. That scares the rest of us. I, for one, don't want to live among people who don't feel safe unless they have the ability to kill (among others) me. I don't want my life to depend on thousands of people never even once momentarily thinking I'm a bad guy.

I know you don't make actual threats to kill people. But there is an implicit threat whenever someone seems to feel that he must have the ability to kill other people, on a moment's notice, all the time. Carrying a gun is not too different from wearing a sign that says, "I can suddenly kill you." If you don't understand this, you're ignoring something important.

Here's an example of a pro-gun argument that is backfiring. Right now, someone is circulating on Facebook a picture of a jump drive, a pocketknife, a lighter, and a pistol. The captions, object by object, are, "Does this make a hacker? A slasher? An arsonist? Inanimate objects don't cause crime."

Well — just in case someone didn't notice — exactly one of those four machines is designed to kill (and maybe designed primarily to kill human beings). So, yes, one of the four is a tool for violence in a way that the other three are not.

Gun advocates need to realize is that an armed society is in between anarchy and civilization. It is not the height of civilization. In civilized surroundings, you don't need to carry your own gun. Anti-gun people need to realize that not all surroundings are civilized.

And furthermore, if you arm everyone, are you willing to bet that not one of them will ever make a mistake? That's what concerns me. People with guns, even wise and good people with guns, are not infallible. A tragic mistake of this kind apparently occurred near Atlanta while this discussion was going on.

Simply having more guns around can make a place more dangerous. How much more dangerous? I don't know. As I said earlier, that's a question of fact. Speculation and anecdotes won't answer it.


This Notebook entry was discussed extensively on Facebook. From anti-gun people I got little or no reply, which surprised me. From pro-gun people, though, I got several sustained arguments, some of which were informative, plus a few insults, which I had to delete.

The pro-gun people were surprisingly put off by the fact that I don't see things 100.000% their way. Some of the less sophisticated gun enthusiasts simply demanded that I ignore facts, or were frightened of making any attempt to understand the other side. They talked as if they had memorized a line of argumentation, dared not question it, and were afraid of anyone who did so. To them, the other side needed to be absolutely, totally refuted, not listened to.

One thing that came through loud and clear is that many pro-gun people tell each other that disarming a populace is a step toward enslaving it. First the government comes and takes your guns, and then the government becomes a totalitarian dictatorship after making sure the people can't fight back. People have actually tried to tell me that every gun-control proposal foreshadows a Wounded Knee massacre.

While I understand that concern, I can't swallow it whole. It would imply that the people of Great Britain and Canada are on the verge of being enslaved. Actually, of course, those countries have about as much personal freedom as anywhere, and I see no enslavement on the horizon. Canada is presently the international refugees' favorite country. As for Britain, an important part of British culture is to expect and demand an extremely fair and accountable government. For all our whining in our Declaration of Independence, I don't think George III was a tyrant — I think he was running one of the best governments the world had seen up to that time, but leaving us out of it, and that was our real complaint.

Anyhow, it is the settled law of the land that individuals can't own military weapons or form private armies in the United States. The few people who try are generally acknowledged to be quite dangerous to the rest of us. They are not our defenders.

Please note that I am not in favor of a ban on private gun ownership. But I think equating your pistol with your freedom is extremely naive. This isn't 1776 or even 1876. Nowadays, we keep ourselves free with ballots more than with bullets.

And, I might add, with mass communications. Not only is the pen mightier than the sword, the printing press has beaten dictators and armies many times. And now we have the Internet, which puts more power in the hands of the masses than ever before.

Someone with a gun could kill me. But nobody can remove all my writings from the Internet. They are already archived in multiple countries, and at the first sign of a threat, these archives would become more numerous, and some would be extremely well hidden from authorities, yet widely distributed to interested people. That's the way the Internet works. It's the new "great equalizer." Perhaps the reason I'm not so enamored of guns is that I'm already wielding a much more powerful force for freedom.

2013
January
24-27

The Nodoroc and the funeral

One more note about my late father-in-law, Jim Mauldin. He had American Indian heritage on his mother's side, of which he was very proud, although we don't know much of the particulars.

It is fitting that his funeral was held very close to an Indian site that intrigued him: the Nodoroc or "mud volcano" in Barrow County. Click through to see a map; the Smith Funeral Home is the long L-shaped building to the left (west) of Barrow Memorial Gardens.

2013
January
23

1999 Isuzu Rodeo and Honda Passport
Silencing keyless entry chirp
Disabling horn used by anti-theft alarm

In memory of Jim Mauldin, today I'll publish an automotive tip — pertaining, in fact, to his car, which I had borrowed for a few days.

Problem #1: The horn chirped every time I used the keyless remote entry system to lock or unlock the car. This noise was unwelcome. I wanted to program it to stay quiet.

Solution: The procedure given on PlanetIsuzoo is the following, slightly different from what is in the instruction manual:

TURNING CHIRP CONFIRMATION ON/OFF

This procedure is for turning the Arm/Disarm confirmation chirp ON or OFF. All steps must be followed carefully. It may take several attempts to sucessfully perform this procedure. Perform these steps as quickly as possible.

1: Close all doors

2: Open the driver's door

3: Insert key in the driver's door lock.

4: Turn key to lock-center-unlock (left-center-right) 3 times, in one-second intervals

5: Close and open the driver's door 2 times, in one second intervals. (Door pin switch may be toggled instead.)

6: Turn key to lock-center-unlock (left-center-right) 3 times, in one-second intervals

7: Close and open the driver's door. RESPONSE: The doors will lock and unlock 1 time.

My added remarks: You will have to try this several times. For me, the fifth and fastest attempt was the one that worked, as shown by a response from the electric door locks. This is an example of what I call "using a human being as a serial UART" — a microcontroller wants a series of pulses, so why not have a human being generate them? Fortunately, most microcontroller engineers have wisely moved away from this practice.

Problem #2: The anti-theft system was occasionally false-triggering, embarrassing me with blinking lights and a honking horn.

Solution: I learned that the alarm system has its own horn (also used for the keyless entry chirps) and concluded that it would be enough to silence the alarm (letting it continue to blink the lights if it went off). That would give me some anti-theft protection and give me time to diagnose the real cause of the problem.

The alarm horn is not the one behind the front grille. It is just inside the passenger side fender, under the hood, right under the open-hood sensor. I disconnected it. Peace and quiet! (And blinking lights, occasionally!)

2013
January
22

James Elmo Mauldin, Jr., 1938-2013




We are sad to report the passing of Melody's father, James Elmo (Jim) Mauldin, Jr., shortly before midnight on January 22, after a long struggle with chronic obstructive pulmonary disease. He died at home, in the presence of his wife and daughter and a hospice nurse. The management of his last days was a testimony to modern hospice care; he maintained his dignity, was free of pain, and was lucid when awake, though toward the end he was only awake for a few minutes at a time. He was mentally and spiritually prepared to an unusual degree.

Jim (as I called him, by his own choice) was half a generation younger than my own parents, who were older than average when I was born. So instead of belonging to the generation that won World War II, he belonged to the generation that savored the fruits of victory. After high school in Thomaston, Georgia (where he met and married Melody's mother), he moved to Atlanta to study engineering at Southern Tech, but in fact worked for United Press International as a teletype operator. When UPI wanted to transfer him in 1972, he bought a Western Auto franchise in Winder, Georgia, and that's where I found the Mauldins when I started going out with Melody. Later he worked for a bank, then retired and pursued woodworking, model aircraft, and computer hobbies.

Like many of his generation, he was fascinated with technology. One of our last conversations was about how the mid-1950s (his high-school years) were an excellent time to be an automotive enthusiast. In those days, you could understand every single part of a car, and even make most of them in a machine shop.

I briefly noted his 50th wedding anniversary a few years ago. Jim and Eleanor were middle-school sweethearts and took it for granted that marriage was a serious, lifelong commitment. They have been an inspiration to us all.

One last note. Jim was an avid reader of this blog. It is therefore appropriate that this is his first published obituary.
2013
January
21

Moon and Jupiter

The moon passed unusually close to Jupiter in the sky this evening. (Not unusually close to it in space, of course; the moon is much closer to us than Jupiter is.) This is a quick fixed-tripod exposure with a Canon 300-mm lens and 1.4× converter. On the original image, a couple of stripes were faintly visible on Jupiter.

2013
January
17-20

Will health-care costs go down?

This article makes some interesting points about the federal budget, especially concerning health-care costs.

I have long suspected that health-care costs are in a "bubble" due to a flurry of major inventions and discoveries, and that further technological advances will lower costs rather than raise them. (Look at what happened to computer costs.) Now I can give a couple more reasons why costs might fall.

One is that medical researchers are learning that recent, expensive inventions, especially tests, are overused. They're learning when not to use them. Look for example at these guidlines. You no longer get a fiberoptic endoscopy just because you have persistent heartburn. Fiberoptic endoscopy is a godsend — but now they're learning, from large-scale statistical studies, how to tell which patients almost certainly don't need one. The same goes for numerous other tests and expensive medications.

The other is insurance reform. Nobody thinks Obamacare is quite the right thing — but it has spurred continuing interest in reinventing medical insurance. We've gone from limited medical insurance 50 years ago, to extremely generous and loosely organized insurance (in the past few years), and now it's time for something else. Exactly what, I have no idea. But insurance companies are in a position to control costs — they have the information needed to do it. Individual patients don't.



Two very short political rants

(1) As long as you see everything as left-wing or right-wing, you will not see much. As I've said before, I don't want conservative facts or liberal facts, I want fact facts.

(2) Distorting facts is not a virtuous act, even if done for a virtuous political goal. There is entirely too much gossip and fabrication coming to us from political activists — and the farther they are from the center, in either direction, the worse it gets. This includes people who pass on unchecked but inflammatory "facts," not just the people who make them up in the first place.

2013
January
16

Another visit from the lizard

The lizard who was our temporary pet during a recent cold spell came out to play on a recent warm day. He had apparently hibernated right in the outside closet where I released him. Now he'll have time to find a good hibernating place for the rest of the winter.

2013
January
13-15

New trend: Darker screens
Also, how to use an OpenFileDialog in a C# console app

Back in the Day, computer screens were dark, with glowing green, yellow, or white letters. Then came the Macintosh and Windows era. Largely to overcome reflections on rather dim screens, computer displays became black-on-white. The idea was to get as much of the screen as bright as possible.

Time has passed, and computer screens have gotten brighter, and brighter, and brighter, and some are now so bright that they're not exactly easy on the eyes. So the latest trend is toward dark user interfaces. An example is the "dark theme" in Visual Studio 2012, which you see here:

Not bad. By the way, the program you see here is an example of how to use an open file dialog in a C# console application. You have to declare the main program STAThread and you have to add a reference to PresentationManager. Then, just use Microsoft.Win32.OpenFileDialog the same way as in a WPF app.

Why would anybody want to do such a thing? Because console mode is handy for quickly written, one-off programs for performing file conversions and the like, but the ability to pick your filenames from a file dialog is very handy in the same situation.

2013
January
11-12

A word we should be using more: "reactionary"

A lot of what calls itself conservative politics today is nothing of the sort. It is reactionary politics. A conservative wants to conserve what has worked well. A reactionary just wants to get as far as possible away from "liberals" even if it takes him into unknown territory.

We're hearing from reactionaries, not conservatives, when people seem to live in a fantasy of the Wild West, or their entire economic policy is little more than "don't tax me," or they long for the government of the 1820s, when the United States was a poor and insecure nation.

We are definitely hearing from reactionaries when we hear arguments against gun control that are purely emotional ("my cold dead hands"), with no attention to facts about modern conditions or human nature. [Note that I'm not taking a position on gun control here, just making a remark about types of arguments.] Conservatism is fact-based (you have to know what you want to conserve). Reactionary politics is partly imaginary.

I am a conservative. I want to preserve the successes and the wisdom of the past. Paraphrasing G. K. Chesterton, conservatism is how we allow our predecessors to vote.

By today's standards, I am not right-wing enough for some conservatives today. I don't devote myself to rooting out "liberals" and trying to be the exact opposite. I figure the exact opposite of a mistake is very often another mistake.

2013
January
9-10

About that trillion-dollar coin idea...

I don't always agree with Paul Krugman, but in this New York Times column he says very sensible things. And along the way, he explains the proposed trillion-dollar-coin trick.

We don't need a debt ceiling. We need a balanced budget. The budget and the debt ceiling both come from Congress. The debt ceiling is merely an obstacle Congress has put in its own path.

There must be people at the Mint trying to figure out how they're going to make a trillion-dollar coin, or a thousand billion-dollar coins, or something, just in case they are told to actually do it. It reminds me of the time the Royal Canadian Mint made a two-foot-diameter million-dollar gold coin, intended as a temporary display, but ended up selling about five of them at a handsome profit!

2013
January
8

"Good afternoon, and welcome to Computer Science 8570."

Today (Jan. 8) I said those words for the last time; it was the first day of the last course I will teach before retirement. Details of the course are here.

It was a surreal experience. The University gave me the biggest classroom I've ever taught in, a room I had not seen before. Room 400 in the Chemistry Building is a recently remodeled room that seats 100. It has comfortable seats, three kinds of projectors, and quite a few audiovisual aids I haven't explored yet. I particularly like the document camera, which lets me put a book or handout on the screen while talking about it.

And I had four students present. One more is coming tomorrow, but one of the ones present today has subsequently dropped the course. There were 12 on the roll, but some of them had signed up for this course as a placeholder while waiting for spaces in a different one that meets at the same time of day.

I had hoped for a larger class, but it makes sense that students who are not going to be able to do theses with me are not taking the course that would prepare them to do so.

2013
January
3-7

Has Adobe Photoshop CS2 become freeware?

This is a fast-developing situation, and what I'm saying here is surely not the last word.

Today (Jan. 7), word spread across the Internet, through major news media, that Adobe Photoshop CS2 was being given away free by the manufacturer.

No, I don't mean the 30-day free trial version that you can always download. I mean Photoshop CS2 with an activation serial number to do a full, unrestricted installation.

CS2 is the version from several years ago. The Windows version runs fine on present-day PCs. The Macintosh one does not run under today's MacOS.

This was not a hoax, but it also apparently wasn't quite true.

The Adobe download link is here and the server was overloaded all day. From it, you could (and probably still can) download Photoshop CS2, or maybe even the whole Creative Suite 2, together with a valid serial number for activating it. I heard from several people who did it successfully.

The catch? Now Adobe says they didn't intend to give CS2 away free. Read this message. I quote:

On behalf of Adobe Systems Incorporated ...

You have heard wrong! Adobe is absolutely not providing free copies of CS2!

What is true is that Adobe is terminating the activation servers for CS2 and that for existing licensed users of CS2 who need to reinstall their software, copies of CS2 that don't require activation but do require valid serial numbers are available. (Special serial numbers are provided on the page for each product download.) See http://forums.adobe.com/thread/1114930.

You are only legally entitled to download and install with that serial number if you have a valid license to the product!

Well then... I have not actually seen the download page, but at best, they are doing "honor system" enforcement, and more likely, they made the license conditions so easy to overlook that lots of people, in good faith, failed to see them.

This puts Adobe into a dubious legal position. Not only am I not a lawyer, but I also have not actually seen the download page, so I'm only speculating. But they may have to resolve it by releasing CS2 as freeware after all. Let's see what happens.

[Addendum:] I think what happened is that Adobe inadvertently set up their download page so that it can be reached without going through several previous pages that would explain the situation and require a login. People have definitely downloaded CS2 without logging in and without being told that it is only for people already licensed.

Legally, I think what happened is that they have inadvertently given away a large number of free copies but have not lost their copyright. They always give away a few free copies of a product (to reviewers and testers). The people who receive free copies are not entitled to distribute them further.

2013
January
2

Two brief, but controversial, political remarks

(1) People who are well informed about political and economic issues are often neither "liberal" nor "conservative." Thoughtful solutions do not fit into categories made up by less-informed people.

(2) Sudden, radical shifts in policy are emotionally satisfying to the people who advocate them, but they carry huge hidden costs. As far as possible, policy changes should be made gradually. To solve our federal budget problem, we need years of steady progress in the right direction, not a sudden dramatic show of austerity.

2013
January
1

Screen updates in WPF, the wrong way and the right way

[Revised.]


1. The problem

As I noted a while back, one of the frustrations of Windows' new WPF user interface is that there seems to be no way to update the screen. In the older WinForms interface, the screen updates automatically and frequently, so this code (for example) will keep writing the date and time in a text box:

while (DateTime.Now < stoptime)
{
    System.Threading.Thread.Sleep(1000);
    textBox1.AppendText(DateTime.Now.ToString() + "\n");
}

Not so in WPF. There, the whole screen freezes until the loop finishes, and then you see all the output at once.

What's going on? The key to the problem is that WPF is fundamentally multithreaded and gives the GUI a thread all to itself. Further, the GUI thread maintains a queue of things to do, and it won't perform an update while it is busy doing your computation. This is actually a good thing, not a bad thing. It keeps the GUI more responsive when you do things the right way (described below).

WinForms is much more eager to include a visible update as part of the operation that triggers it (such as AppendText). If it doesn't, you can do this.Update() to prod it along. Not so WPF. In WPF, the screen is only updated after the program finishes responding to your events, such as the button click that performs a long computation.


2. The wrong solution

You can force the GUI thread to update the screen. In WinForms, you would call Application.DoEvents(), but WPF doesn't have that. Instead, you can do the following (which is based on an idea in Noble, Bourton, and Jones, WPF Recipes in C# 2008, but simplified a little by me).

using System.Windows.Threading;

private void button1_Click(object sender, RoutedEventArgs e)
{
   // Make sure the user doesn't launch this *again*
   // while it's already running
   button1.IsEnabled = false;
   // Note: The button goes inactive immediately but
   // does not turn gray until the screen updates

   // For the following 10 seconds we will do this...
   DateTime stoptime = DateTime.Now.AddSeconds(10);
   while (DateTime.Now < stoptime)
   {
      // Simulate some time-consuming work and report a result
      System.Threading.Thread.Sleep(1000);
      textBox1.AppendText(DateTime.Now.ToString() + "\n");

      // Clear the event queue so the screen will update
      Dispatcher.CurrentDispatcher.Invoke(
            DispatcherPriority.Background,
            new Action(() => { return; })
      );
   }

   // All done, so re-enable the button
   button1.IsEnabled = true;
   // The screen will update again now because
   // we are finished handling the button click
}

What on earth is going on here? Well, to start with,

() => { return; }

is a do-nothing function, like void f() { return; } but written in lambda notation. You're telling the thread dispatcher to call this function with Background priority (the lowest) and to wait until it finishes (Invoke). That means this function will run after everything else that is already in the queue for the GUI to execute, and nothing else will happen until it's done. Voilà — the GUI finally gets caught up, and the screen refreshes.

But that's a kluge. It results in sluggish response; the first update may take two or three seconds, although subsequent updates are faster.



3. The right solution

The right approach, as pointed out to me by Karthik Nadig of Microsoft, is to run your computation in the background, on a separate thread. You can even provide a "cancel" button to stop it while it runs.

The easiest way to do this is the BackgroundWorker object type. Here's the code for a simple example:

using System.ComponentModel;

BackgroundWorker bw;

// Runs in the GUI (main) thread, as button event handler.
private void button1_Click(object sender, RoutedEventArgs e)
{
    // This is either the start button or the stop (cancel) button, depending...
    if (bw != null && bw.IsBusy)
    {
        // Set the cancel bit on the BackgroundWorker if it's already running
        bw.CancelAsync();
    }
    else
    {
        // Tend to the screen appearance
        textBox1.Cursor = this.Cursor = Cursors.Wait;
        button1.Content = "STOP"; // label it as the stop button
        button1.Cursor = Cursors.Arrow; // allow people to point to it

        // Initialize the BackgroundWorker
        bw = new BackgroundWorker
        {
            WorkerReportsProgress = true,
            WorkerSupportsCancellation = true
        };

        // Event handlers for starting, reporting progress, and finishing
        bw.DoWork += new DoWorkEventHandler(bw_DoWork);
        bw.ProgressChanged +=
                new ProgressChangedEventHandler(bw_ProgressChanged);
        bw.RunWorkerCompleted +=
                new RunWorkerCompletedEventHandler(bw_RunWorkerCompleted);

        // Set it going
        bw.RunWorkerAsync();
    }
    // Screen updates upon EXIT from this event handler.
    // Background process continues running.
}

// Runs in the BackgroundWorker's thread; cannot access the screen directly.
void bw_DoWork(object sender, DoWorkEventArgs e)
{
    // For the following 10 seconds we will do this, unless cancelled...
    DateTime stoptime = DateTime.Now.AddSeconds(10);
    while (DateTime.Now < stoptime && !bw.CancellationPending)
    {
        // Simulate some time-consuming work and report a result
        System.Threading.Thread.Sleep(1000);
        bw.ReportProgress(0, DateTime.Now.ToString() + "\n");
    }
}

// Runs in the GUI (main) thread.
// Called asynchronously from BackgroundWorker thread.
// Can be called again before it finishes; requests go in queue.
void bw_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
    // When we receive a progress report, add it to the text box
    textBox1.AppendText((string)e.UserState);
    // Could also ScrollToEnd, update a progress bar, etc.
    // Screen updates upon EXIT from this event handler.
}

// Runs in the GUI (main) thread.
// Called when BackgroundWorker thread finishes.
void bw_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
    // When finished, re-label the button as "START" and report conclusion
    textBox1.AppendText("All done.");
    button1.Content = "START";
    textBox1.Cursor = this.Cursor = Cursors.Arrow;
    // Screen updates upon EXIT from this event handler.
}

For the BackgroundWorker you define three event handlers, one for doing its work, one for when it calls ReportProgress, and one for when it finishes. While it runs, it can look for the CancellationPending bit on the BackgroundWorker and terminate itself gracefully. It can receive arguments and return results through the object e.

One word of caution. Don't try to change the screen display constantly — you can overwhelm the GUI thread and make the program unresponsive. It's OK to call ReportProgress as often as you want, but you might want to have the event handler, bw_ProgressChanged, accumulate the data and only write it to the screen at judicious intervals, such as once every second.

Also, note that if the BackgroundWorker crashes, you will not hear about it — it will just stop. That's why I suggest wrapping the computation in a try...catch block that will display the exception or report it back as some kind of status code. Even though it can't directly manipulate the main window, the BackgroundWorker is free to put up a MessageBox, so that is one way to report a crash to the user.

Finally, you don't have to use BackgroundWorker. You can start a computation thread — or several — directly and then use BeginInvoke for cross-thread procedure calls. If you know how to do this, you probably don't need my notes.


Addendum: Data binding does not solve the problem

I spent a long time this afternoon learning how to use data binding in WPF because I thought it might provide another solution to this problem: Bind the text of the textbox to a string in the program, support INotifyPropertyChanged, and then just change the string whenever you want to change what's on the screen.

The answer is, that might be convenient in some other ways, but it doesn't help. Data binding determines what should appear on the screen when the screen is updated. INotifyPropertyChanged says that the data binding should update itself when the code-behind data changes. But that doesn't cause the screen to update until it's due for updating.


If what you are looking for is not here, please look at previous months.