twitter - 高画質 - ツイッター センシティブ 解除




Twitterの画像エンコーディングの挑戦 (10)

1000ワード分の絵があれば、どのくらいの絵を140文字に収めることができますか?

:それは人々です! Bounty締め切りはここにあり、厳しい審議の後、私はBoojumのエントリーが Sam Hocevar'sをほんのわずかに抹殺したと決めました 。 私はそれらを書く機会があった私はより詳細なメモを掲載します。 もちろん、誰もが解決策を提出し続け、人々が投票するためのソリューションを改善し続けることは自由に感じるべきです。 投稿したエントリーとエントリーに感謝します。 私はそれらのすべてを楽しんだ。 これは私が走るのがとても楽しいものでした。そして、エントラントと観客の両方にとって楽しいことを願っています。

私はTwitterのコメントに画像を圧縮しようとしているこの面白い記事に出くわしました。そのスレッド(そしてRedditのスレッド )の多くの人が、あなたがそれをやり遂げることができるさまざまな方法についての提案をしました。 だから、私はそれが良いコーディングの課題になると思う。 人々が自分の口がどこにあるのかお金を入れさせ、エンコーディングについての考え方が、利用可能な限られたスペースでより詳細につながることを示します。

私は140文字のTwitterメッセージに画像をエンコードし、再び画像にデコードするための汎用システムを思いついた。 Unicode文字を使うことができるので、文字あたり8ビット以上が得られます。 ただし、Unicode文字を許可する場合でも、イメージを非常に小さなスペースに圧縮する必要があります。 これは確実に損失の圧縮になります。そのため、各結果の見栄えについて主観的な判断が必要になります。

オリジナルの著者Quasimondoがコード化したものです(画像はCreative Commons Attribution-Noncommercialライセンスでライセンスされています ):

あなたはより良くできますか?

ルール

  1. プログラムには、 エンコードデコードの 2つのモードが必要です。
  2. エンコード時:
    1. あなたのプログラムはあなたが選んだ任意の合理的なラスターグラフィックフォーマットのグラフィックを入力として取らなければなりません。 ImageMagickサポートされているすべてのラスタ形式は妥当であると判断します。
    2. プログラムは、140以下のUnicodeコードポイントで表現できるメッセージを出力する必要があります。 U+FFFEU+FFFFU+ n FFFEU+ n FFFFn10 16進数、範囲はU+FDD0 U+10FFFF 140コードポイントU+FDEF )とサロゲートコードポイント( U+D800 - U+DFFF )を使用します。 それはあなたが選んだ任意の合理的なエンコーディングで出力されます。 GNU iconvサポートされているすべてのエンコーディングは合理的であると考えられ、プラットフォーム固有のエンコーディングまたはロケールエンコーディングは良い選択になるでしょう。 詳細については、以下のUnicodeの注を参照してください。
  3. デコード時:
    1. あなたのプログラムは、あなたのエンコーディングモードの出力を入力として取るべきです。
    2. あなたのプログラムは、上で定義したような任意の合理的なフォーマットで画像を出力しなければなりませんが、出力ベクトルフォーマットはOKです。
    3. 画像出力は入力画像の近似でなければなりません。 あなたが入力画像に近づくほど良いでしょう。
    4. デコードプロセスは、上記で指定された出力以外のエンコードプロセスの他の出力にアクセスすることはできません。 つまり、イメージをどこかにアップロードしてデコードプロセスのURLを出力することはできません。
  4. ユーザーインターフェイスの一貫性のために、プログラムは次のように動作する必要があります。

    1. プログラムは、適切なインタプリタを持つプラットフォーム上で実行可能に設定できるスクリプト、または実行可能ファイルにコンパイルできるプログラムでなければなりません。
    2. あなたのプログラムは、モードを設定decodeために最初の引数としてencodeまたはdecodeいずれかをとる必要があります。
    3. あなたのプログラムは、次のうちの1つ以上の方法で入力する必要があります(ファイル名を指定する場合は、stdinとstdoutから読み書きすることもできます)。

      1. 標準入力から入力を取り、標準出力で出力を生成します。

        my-program encode <input.png >output.txt
        my-program decode <output.txt >output.png
        
      2. 2番目の引数で指定されたファイルから入力を受け取り、3番目に指定されたファイルに出力を生成します。

        my-program encode input.png output.txt
        my-program decode output.txt output.png
        
  5. あなたのソリューションについては、投稿してください:
    1. あなたのコードは完全に、そして/または他の場所でホストされているリンクにリンクすることができます(長すぎる場合やコンパイルするのに多くのファイルが必要な場合など)。
    2. コードからすぐにわからない場合や、コードが長く、人々が要約に興味がある場合、その仕組みについての説明。
    3. 原画像、圧縮されたテキスト、デコードされた画像のサンプル画像。
    4. あなたが他人が持っていたアイデアに基づいて構築しているのであれば、それを属性にしてください。 他の人のアイデアを洗練させようとするのは間違いありませんが、あなたそれらを属性付けしなければなりません

ガイドライン

これらは、基本的に壊れているかもしれないルール、提案、スコアリング基準です:

  1. 美学は重要です。 私は審査を行い、他の人が次のことに基づいて審査することを提案します:
    1. 出力画像がどの程度良好に見え、元のように見えるか。
    2. テキストがどれほど素晴らしいか。 本当に巧妙な圧縮方式があれば、完全にランダムなgobbledigookはOKですが、イメージを多言語の詩に変える答えや、賢明なものも見たいと思っています。 元のソリューションの作者は、中国語の文字のみを使用することにしました。
    3. 興味深いコードと巧妙なアルゴリズムは常に良いです。 私は短い、ポイント、そして明確なコードが好きですが、本当に巧妙な複雑なアルゴリズムは良い結果を生む限りOKです。
  2. スピードも重要ですが、イメージを圧縮する仕事がどれだけ重要かは重要ではありません。 私はむしろ、数日のうちに遺伝的アルゴリズムを実行する何かよりも、1/10秒でイメージを変換できるプログラムを持っています。
  3. 私は、合理的に品質に匹敵するものであれば、より長いものに対してはより短い解を好むでしょう。 簡潔さは美徳です。
  4. あなたのプログラムは、Mac OS X、Linux、またはWindows上で自由に利用可能な実装を持つ言語で実装する必要があります。 私は、プログラムを実行することができるようにしたいと思いますが、あなたはMATLABまたは何かの下で実行される素晴らしいソリューションがあれば、それは問題ありません。
  5. あなたのプログラムは可能な限り一般的でなければなりません。 可能な限り多くの異なるイメージで機能するはずですが、一部のイメージでは他のイメージよりも優れた結果が得られる場合があります。 特に:
    1. プログラムにいくつかのイメージが組み込まれていて、それが一致し、参照を書き込んだり、デコード時に一致するイメージを生成したりすることは、かなり不自由なものであり、いくつかのイメージしかカバーしません。
    2. シンプルでフラットな幾何学的形状の画像をいくつかのベクトルプリミティブに分解できるプログラムはかなり気が利いていますが、ある種の複雑さを超えて画像に失敗すると、一般的には不十分です。
    3. 特定の固定アスペクト比の画像しか取ることができないが、それらと良好な仕事をするプログラムもOKですが、理想的ではありません。
    4. 白黒画像は、カラー画像よりも小さな領域に多くの情報を得ることができます。 一方、それはそれが適用可能な画像の種類を制限することがあります。 白と黒の顔が上手く出てきますが、抽象的なデザインはあまりうまくいかないかもしれません。
    5. 出力画像が入力よりも小さい場合、ほぼ同じ割合であるが、それは完全にうまくいく。 画像を拡大して元の画像と比較する必要がある場合は問題ありません。 重要なのはそれがどのように見えるかです。
  6. あなたのプログラムは、実際にTwitterを通過して無傷で出ることができる出力を生成する必要があります。 サポートされている文字の正確なセットについてのドキュメントは見つからなかったので、これはルールではなくガイドラインにすぎませんが、おそらく制御文字、ファンキーな目に見えない結合文字、私用文字などは避けるべきです。

得点表

私の受け入れられたソリューションを選択する際にソリューションをランキングする方法の一般的なガイドとして、私はおそらく25ポイントのスケールでソリューションを評価していると言います(これは非常に荒く、直接何かを採点することはありません。これは基本的なガイドラインとして):

  • エンコード方式が広範囲の入力画像をどれくらいうまく再現しているかについて15ポイント 。 これは主観的で審美的な判断である
    • 0は全く動作しないことを意味し、毎回同じイメージを返します。
    • 5は、いくつかの画像をエンコードできることを意味しますが、デコードされたバージョンは醜く見えますが、より複雑な画像では全く機能しない可能性があります
    • 10は広範囲の画像で動作することを意味し、場合によっては区別可能な快適な画像を生成します
    • 15は、いくつかの画像の完全な複製を生成し、さらに大きく複雑な画像の場合でも、認識可能なものを提供することを意味します。 または、おそらくそれはかなり認識可能な画像を作成しませんが、元の画像からはっきりと分かりやすい美しい画像を生成します。
  • Unicode文字セットを使いやすくするための3ポイント
    • 許可された文字のセット全体を単純に使用するための0ポイント
    • Twitterやさまざまな状況での転送に安全な文字セットを使用する場合は1ポイント
    • 漢字表意文字や右から左への文字のみなど、文字のテーマサブセットを使用する場合は2ポイント
    • 読みやすいテキストを生成する、または問題の画像のように見える文字を使用するなど、本当にすっきりとしたことをする3点
  • 巧妙なアルゴリズムアプローチとコードスタイルのための3つのポイント
    • 画像を縮小するために1000行のコードしかない0点、それを1ピクセルあたり1ビットとして扱い、base64で
    • 標準のエンコーディング手法を使用し、よく書かれ、簡単なものであれば1ポイント
    • 比較的新しいエンコーディング技術を導入したもの、または驚くほど短くてクリーンなものについては2ポイント
    • 実際に良い結果を生み出す1つのライナー、またはグラフィックスエンコーディングの新しい土台を打ち破るもの(3つのポイントは、新しい土台を打ち破るためのポイント数が少ないようだが、その結果が美学にとって高いスコアを持つ可能性があることを覚えている)同様に)
  • 速度は2ポイント 。 他のすべてが等しい、より速い方が良いですが、上記の基準はすべてスピードよりも重要です
  • フリーソフトウェア(オープンソース)を使用すると1ポイントとなります。私はフリーソフトウェアを優先します(ただし、Mono上で実行されている限りC#はこのポイントに適格であり、同様にMATLABコードはGNU Octave上で動作します)
  • すべてのルールに実際に従うための1ポイント 。 これらのルールは少し大きく複雑になっているので、細かいところが間違っているような良い答えはおそらく受け入れますが、実際にはすべてのルールに従った解決策を追加します

参照画像

いくつかの人々はいくつかの参照画像を求めてきました。 試してみることができるいくつかの参考画像を以下に示します。 より小さなバージョンがここに埋め込まれています。これらのバージョンは、必要に応じてより大きなバージョンのイメージにリンクします。

私は上記の基準に基づいて、私が一番好きなソリューションのために、 500の報奨金 (さらにStackOverflowが起動する50)を提供しています。 もちろん、他の人たちも自分の好きなソリューションに投票することをお勧めします。

締切日の注意

このコンテストは、5月30日土曜日の午後6時ごろ、賞金がなくなるまで続きます。終了する正確な時間は言うことができません。 それは午後5時から午後7時の間です。 私は午後2時に提出されたすべてのエントリーを見ることを保証し、午後4時までに提出されたすべてのエントリーを見るように最善を尽くします。 それ以降に解決策が提出された場合、私は自分の決定を下す前に、彼らに公平な見方を与えるチャンスがないかもしれません。 また、早期に提出すればするほど、最高の解決策を選ぶ手助けをするために投票するチャンスが増えるので、締め切りになるより早く提出してください。

Unicodeノート

また、Unicode文字がどんなものであるかを正確に混同しています。 可能なUnicodeコードポイントの範囲はU+10FFFFです。 オープンなデータの交換でUnicode文字として使用することは決してできないコードポイントがいくつかあります。 これらは非文字代理コードポイントです。 非文字は、 U+FFFEU+FFFFU+ n FFFEU+ n FFFFn10 16進数)、 U+FDD0 - U+FDEF範囲としてUnidode Standard 5.1.0セクション16.7で定義されています。 これらの値は、アプリケーション固有の内部使用に使用されることを意図しており、適合するアプリケーションは、処理されたテキストからこれらの文字を取り除く可能性があります。 UTF-16のBasic Multilingual Plane以外の文字のエンコードには、 U+D800 - U+DFFFようにUnicode Standard 5.1.0セクション3.8で定義されている代理コードポイントが使用されます。 したがって、これらのコードポイントをUTF-16エンコーディングで直接表現することは不可能であり、他のエンコーディングでエンコードすることは無効です。 したがって、このコンテストの目的のために、上記で定義されたすべての非文字とサロゲートのペアを除いて、 U+0000 - U+10FFFF範囲の140 Unicodeコードポイントのシーケンスにイメージをエンコードするプログラムを許可します。

私は、割り当てられた文字だけを使用するソリューションや、割り当てられた文字の賢明なサブセットを使用するか、または使用する文字セットで興味深いものを使用する優れたソリューションを好むでしょう。 割り当てられた文字のリストについては、 Unicode文字データベースを参照してください。 一部の文字は範囲の開始と終了としてのみリストされていますが、一部の文字は直接表示されています。 また、サロゲート・コード・ポイントはデータベースにリストされていますが、上記のように禁止されています。 出力するテキストをより興味深くするために、文字の特定の特性を利用したい場合は、 名前付きコードブロックのリストさまざまな文字プロパティなど、 さまざまな文字 情報のデータベースが利用できます

Twitterはサポートしている文字セットを正確に指定していないので、特定の文字が余分な文字や特定の文字を削除するため、Twitterで実際には動作しないソリューションについては寛大な扱いとなります。 Twitterや他のマイクロブログサービス( identi.caなど)を使用して、コード化されたすべての出力を無断で転送できることが望ましいが、必須ではない。 私は、Twitterのエンティティエンコーディング<、>、&の4つ、4つ、5つの文字をそれぞれ数えますが、私自身はテストしていません。そのように数えます

ヒントとリンク

  • ルール内の有効なUnicode文字の定義は少し複雑です。 CJK統一看板(U + 4E00-U + 9FCF)などの文字の1ブロックを選択する方が簡単かもしれません。
  • 画像操作のために、 ImageMagickPython Imaging Libraryのような既存の画像ライブラリを使用することができます。
  • Unicode文字セットとそのさまざまなエンコーディングを理解するための助けが必要な場合は、 このクイックガイドまたはLinuxおよびUnixのUTF-8に関する詳細FAQを参照してください。
  • 早期にソリューションを入手すればするほど、私は(そして他の人々が投票する)時間を見なければなりません。 ソリューションを改善したら編集することができます。 私は解決策を通して私の最後の一見を取るとき、私の賞金を最新のバージョンに基づいています。
  • 簡単な画像フォーマットを解析して書きたい場合(そして既存のフォーマットを使用したくない場合)は、 PPMフォーマットの使用をお勧めします 。 これは非常に扱いやすいテキストベースのフォーマットであり、 ImageMagickを使って変換することができます。

nanocrunch.cppありnanocrunch.cpp 、ここに私のものがあります: nanocrunch.cppCMake.を使ってビルドするCMakeLists.txtファイルCMake. 画像処理の大部分をMagick++ ImageMagick APIに依存しています。 また、文字列エンコーディングのためのbignum算術演算のためのGMPライブラリが必要です。

私はフラクタル画像の圧縮を解き、いくつかのユニークな歪みに基づいて解決しました。 基本的なアイデアは、画像を撮り、コピーを50%に縮小し、元の画像の重なり合わないブロックに似ている様々な向きの部分を探します。 この検索には非常に力強いアプローチが必要ですが、変更を導入するほうが簡単です。

最初の変更点は、90度の回転と反転を見るのではなく、私のプログラムでは45度の向きも考慮しているということです。 ブロックあたり1ビット多くなりますが、画質に非常に役立ちます。

もう1つは、各ブロックの色成分ごとにコントラスト/明るさの調整を保存するにはコストがかかりすぎるということです。 代わりに、私は多量の量子化された色を保存します(パレットには4 * 4 * 4 = 64色しかありません)。 数学的には、これは各色の明るさとコントラストを可変することと同じです。 残念なことに、それはまた、色を反転させるために負のコントラストがないことを意味します。

各ブロックの位置、方向、色を計算したら、これをUTF-8文字列にエンコードします。 第1に、ブロックテーブル内のデータと画像サイズを表す非常に大きなbignumを生成します。 これに対するアプローチはSam Hocevarのソリューションに似ています。位置によって異なる基数を持つ多数の種類です。

次に、使用可能な文字セットのサイズが何であれ、それをベースに変換します。 デフォルトでは、割り当てられたUnicode文字セットから、より小さい、より大きい、アンパサンド、制御、結合、および代理および非公開文字を使用します。 それはかなりではありませんが、それは動作します。 また、デフォルトのテーブルをコメントアウトし、印字可能な7ビットASCII(<、>、&文字を除く)またはCJK統一イデオグラフを選択することもできます。 使用可能な文字コードの表は、無効で有効な文字を交互に繰り返してランレングス符号化されて格納される。

とにかく、私の古い3.0GHz P4で測定されたような画像と時間があり、上記で説明した完全なユニコードセットで140文字に圧縮されています。 全体的に、私はかなり彼らがすべてどのように判明したことに満足しています。 これに取り組む時間があれば、圧縮解除された画像のブロック性を減らそうとしています。 それでも、私は結果が極端な圧縮率にはかなり良いと思います。 圧縮解除されたイメージはビット印象ですが、ビットが元のイメージとどのように対応しているかは比較的簡単です。

スタックオーバーフローのロゴ(8.6秒でエンコード、7.9秒でデコード、485バイト):
http://i44.tinypic.com/2w7lok1.png

レナ(32.8秒エンコード、13.0秒デコード、477バイト):
http://i42.tinypic.com/2rr49wg.png http://i40.tinypic.com/2rhxxyu.png

モナリザ(43.2秒でエンコード、14.5秒でデコード、490バイト):
http://i41.tinypic.com/ekgwp3.png http://i43.tinypic.com/ngsxep.png

編集:CJK統一文字

SamはCJKでこれを使用することについてコメントで尋ねました。 モナリザのバージョンは、CJKユニファイドキャラクタセットから139文字に圧縮されています:

http://i43.tinypic.com/2yxgdfk.png詠璘驞脒脒鵚蛥朐朐朐朐瀦瀦魷魷栘璯緍脲蕜抱揎頻肩束鑡嗞靊柮嚛嚵籥聚隤慛銓銓馿櫰櫰矍鰛掾撄粂敽稉蔍蔍螎葙葙峬惫冧笻哜搀澐譶辍澮垝黟偞竽竽梀韠镰猳閺狌羶羶喙伆杇婣婣鐤鐤鐤諽諽鷍鴞駫駫搶毤毤埙誖萜愿愿愿愿愿愿愿愿愿愿愿愿愿愿愿愿愿愿愿愿愿擸萿

私がこれに使用したプログラムの先頭のチューニングパラメータは、19,19,4,4,10,10,11,1000,1000でした。私はnumber_assignedとコードの最初の定義をコメントアウトし、 CJKユニファイドキャラクタセットを選択するための最後の定義。


イメージファイルとpythonソース (バージョン1と2)

バージョン1これは私の最初の試みです。 私が行くように私は更新されます。

私は300文字までのロゴをほとんどロスレスにしています。 私の技法は、SVGベクトルアートへの変換を使用しているので、ラインアートで最も効果的です。 これは実際にはSVGコンプレッサーですが、依然としてオリジナルアートがベクトル化の段階を経る必要があります。

私の最初の試みでは、PNGトレース用のオンラインサービスを使用しましたが、 potrace (オープンソース)を含むこの部分を処理できる無料で非フリーのツールがpotraceます。

ここに結果があります

元のSOロゴhttp://www.warriorhut.org/graphics/svg_to_unicode/so-logo.pngオリジナルのデコードされたSOロゴhttp://www.warriorhut.org/graphics/svg_to_unicode/so-logo-decoded.pngエンコード後デコード

キャラクター数:300

時間 :測定されていませんが、実際には瞬間的です(ベクトル化/ラスタライズステップは含まれません)

次の段階は、ユニコード文字ごとに4つのシンボル(SVGパスポイントとコマンド)を埋め込むことです。 現時点では、私のpythonビルドには、文字ごとの解像度を制限するワイド文字サポートUCS4がありません。 私はまた、最大範囲をユニコードの予約範囲0xD800の下限に制限しましたが、一度許可された文字のリストとそれを避けるフィルタを作成したら、理論的に必要な文字の数を70〜上記のロゴ

現在、この方法の限界は、出力サイズが固定されていないことです。 ベクトル化後のベクトルノード/ポイントの数に依存します。 この制限を自動化するには、イメージをピクセル化して(ベクターの主な利点を取り除く)、または単純化段階を経て目的のノード数に達するまでパスを繰り返し実行する必要があります(私は現在Inkscapeで手動で行っています)。

バージョン2

更新 :v2は現在競争する資格があります。 変更点:

  • コマンドライン制御の入出力とデバッグ
  • XMLパーサ(lxml)を使用して正規表現の代わりにSVGを処理する
  • ユニコード記号ごとに2つのパスセグメントをパックする
  • 文書化とクリーンアップ
  • サポートスタイル= "塗りつぶし:色"と塗りつぶし= "色"
  • ドキュメントの幅/高さを1文字にまとめる
  • 単一の文字にパックされたパスの色
  • カラー圧縮は、色ごとに4ビットのカラーデータをスローし、16進変換を介して文字にパッキングすることによって達成されます。

キャラクター133

時間 :数秒

v2でデコードされたものhttp://www.warriorhut.org/graphics/svg_to_unicode/so-logo-decoded-v2.pngエンコードとデコード後(バージョン2)

ご覧のとおり、今回はアーティファクトがいくつかあります。 それは方法の制限ではなく、私のコンバージョンのどこかでの間違いです。 アーチファクトは、ポイントが0.0〜127.0の範囲を外れたときに発生し、それらを制約しようとする試みが混ざり合っています。 解決策は単純に画像を縮小することですが、アートボードやグループマトリックスではなく実際のポイントを拡大するのに問題がありました。気にするのはあまりにも疲れました。 要するに、あなたのポイントがサポートされている範囲内にあれば、一般的に動作します。

私は、中央のねじれは、それがリンクされているハンドルの反対側にハンドルが移動していることによると信じています。 基本的に、ポイントはあまりにも最初から密接しています。 圧縮前にソースイメージ上に単純化フィルタを実行すると、これを修正して不要な文字を削ってください。

UPDATE :このメソッドは単純なオブジェクトでは問題ないので、複雑なパスを単純化してノイズを減らす方法が必要でした。 私はこの作業にInkscapeを使用しました。 私はInkscapeを使って不必要なパスを整理することに運がありましたが、それを自動化する時間はありませんでした。 私はパスの数を減らすためにInkscape 'Simplify'関数を使っていくつかのサンプルを作成しました。

簡素化はうまくいくが、この多くのパスでは遅くなる可能性がある。

オートトレースの 例http://www.warriorhut.org/graphics/svg_to_unicode/autotrace_16_color_manual_reduction.png コネルボックス http://www.warriorhut.com/graphics/svg_to_unicode/cornell_box_simplified.png lena http://www.warriorhut.com/graphics /svg_to_unicode/lena_std_washed_autotrace.png

サムネイルは追跡されたhttp://www.warriorhut.org/graphics/svg_to_unicode/competition_thumbnails_autotrace.png

ここにいくつかの超低解像度ショットがあります。 いくつかの巧妙なパス圧縮が必要であるかもしれないが、これらは140文字の制限に近いでしょう。

グルーミングされたhttp://www.warriorhut.org/graphics/svg_to_unicode/competition_thumbnails_groomed.png簡略化されていない

三角形分割されたもの。http://www.warriorhut.org/graphics/svg_to_unicode/competition_thumbnails_triangulated.png簡略化された、スペックル除去され、三角形分割されたもの。

autotrace --output-format svg --output-file cornell_box.svg --despeckle-level 20 --color-count 64 cornell_box.png

上: autotraceを使った簡略化されたパス。

残念ながら、私のパーサはオートトレース出力を処理しないので、ポイントが使用されているかどうか、またはどれだけ単純化するか分からず、悲しいことに締め切り前にそれを書く時間がほとんどありません。 それは、しかし、inkscapeの出力よりも解析する方がはるかに簡単です。


Idea: Could you use a font as a palette? Try to break an image in a series of vectors trying to describe them with a combination of vector sets (each character is essentially a set of vectors). This is using the font as a dictionary. I could for instance use al for a vertical line and a - for a horizontal line? ちょうどアイデア。


In the original challenge the size limit is defined as what Twitter still allows you to send if you paste your text in their textbox and press "update". As some people correctly noticed this is different from what you could send as a SMS text message from your mobile.

What is not explictily mentioned (but what my personal rule was) is that you should be able to select the tweeted message in your browser, copy it to the clipboard and paste it into a text input field of your decoder so it can display it. Of course you are also free to save the message as a text file and read it back in or write a tool which accesses the Twitter API and filters out any message that looks like an image code (special markers anyone? wink wink ). But the rule is that the message has to have gone through Twitter before you are allowed to decode it.

Good luck with the 350 bytes - I doubt that you will be able to make use of them.


Posting a Monochrome or Greyscale image should improve the size of the image that can be encoded into that space since you don't care about colour.

Possibly augmenting the challenge to upload three images which when recombined give you a full colour image while still maintaining a monochrome version in each separate image.

Add some compression to the above and It could start looking viable...

Nice!!! Now you guys have piqued my interest. No work will be done for the rest of the day...


Regarding the encoding/decoding part of this challenge. base16b.org is my attempt to specify a standard method for safely and efficiently encoding binary data in the higher Unicode planes.

Some features :

  • Uses only Unicode's Private User Areas
  • Encodes up to 17 bits per character; nearly three times more efficient than Base64
  • A reference Javascript implementation of encode/decode is provided
  • Some sample encodings are included, including Twitter and Wordpress

Sorry, this answer comes way too late for the original competition. I started the project independently of this post, which I discovered half-way into it.


The following is my approach to the problem and I must admit that this was quite an interesting project to work on, it is definitely outside of my normal realm of work and has given me a something new to learn about.

The basic idea behind mine is as follows:

  1. Down-sample the image gray-scale such that there were a total of 16 different shades
  2. Preform RLE on the image
  3. Pack the results into the UTF-16 characters
  4. Preform RLE on the packed results to remove any duplication of characters

It turns out that this does work, but only to a limited extent as you can see from the sample images below. In terms of output, what follows is a sample tweet, specifically for the Lena image shown in the samples.

乤乤万乐唂伂倂倁企儂2企倁3企倁2企伂8企伂3企伂5企倂倃伂倁3企儁企2伂倃5企倁3企倃4企倂企倁企伂2企伂5企倁企伂쥹皗鞹鐾륶䦽阹럆䧜椿籫릹靭욶옷뎷歩㰷歉䴗鑹㞳鞷㬼獴鏙돗鍴祳㭾뤶殞焻 乹Ꮛ靆䍼

As you can see, I did try and constrain the character set a bit; however, I ran into issues doing this when storing the image color data. Also, this encoding scheme also tends to waste a bunch of bits of data that could be used for additional image information.

In terms of run times, for small images the code is extremely fast, about 55ms for the sample images provided, but the time does increase with larger images. For the 512x512 Lena reference image the running time was 1182ms. I should note that the odds are pretty good that the code itself isn't very optimized for performance (eg everything is worked with as a Bitmap ) so the times could go down a bit after some refactoring.

Please feel free to offer me any suggestions on what I could have done better or what might be wrong with the code. The full listing of run times and sample output can be found at the following location: http://code-zen.info/twitterimage/

Update One

I've updated the the RLE code used when compressing the tweet string to do a basic look back and if so so use that for the output. This only works for the number value pairs, but it does save a couple of characters of data. The running time is more or less the same as well as the image quality, but the tweets tend to be a bit smaller. I will update the chart on the website as I complete the testing. What follows is one of the example tweet strings, again for the small version of Lena:

乤乤万乐唂伂倂倁企儂2企倁3企倁ウ伂8企伂エ伂5企倂倃伂倁グ儁企2伂倃ガ倁ジ倃4企倂企倁企伂ツ伂ス倁企伂쥹皗鞹鐾륶䦽阹럆䧜椿籫릹靭욶옷뎷歩㰷歉䴗鑹㞳鞷㬼獴鏙돗鍴祳㭾뤶殞焻 乹Ꮛ靆䍼

Update Two

Another small update, but I modified the code to pack the color shades into groups of three as opposed to four, this uses some more space, but unless I'm missing something it should mean that "odd" characters no longer appear where the color data is. Also, I updated the compression a bit more so it can now act upon the entire string as opposed to just the color count block. I'm still testing the run times, but they appear to be nominally improved; however, the image quality is still the same. What follows is the newest version of the Lena tweet:

2乤万乐唂伂倂倁企儂2企倁3企倁ウ伂8企伂エ伂5企倂倃伂倁グ儁企2伂倃ガ倁ジ倃4企倂企倁企伂ツ伂ス倁企伂坹坼坶坻刾啩容力吹婩媷劝圿咶坼妛啭奩嗆婣冷咛啫凃奉佶坍均喳女媗决兴宗喓夽兴唹屹冷圶埫奫唓坤喝奎似商嗉乃

Logo http://code-zen.info/twitterimage/images/-logo.bmp Cornell Box http://code-zen.info/twitterimage/images/cornell-box.bmp Lena http://code-zen.info/twitterimage/images/lena.bmp Mona Lisa http://code-zen.info/twitterimage/images/mona-lisa.bmp


The following isn't a formal submission, since my software hasn't been tailored in any way for the indicated task. DLI can be described as an optimizing general purpose lossy image codec. It's the PSNR and MS-SSIM record holder for image compression, and I thought it would be interesting to see how it performs for this particular task. I used the reference Mona Lisa image provided and scaled it down to 100x150 then used DLI to compress it to 344 bytes.

Mona Lisa DLI http://i40.tinypic.com/2md5q4m.png

For comparison with the JPEG and IMG2TWIT compressed samples, I used DLI to compress the image to 534 bytes as well. The JPEG is 536 bytes and IMG2TWIT is 534 bytes. Images have been scaled up to approximately the same size for easy comparison. JPEG is the left image, IMG2TWIT is center, and DLI is the right image.

Comparison http://i42.tinypic.com/302yjdg.png

The DLI image manages to preserve some of the facial features, most notably the famous smile :).


The idea of storing a bunch of reference images is interesting. Would it be so wrong to store say 25Mb of sample images, and have the encoder try and compose an image using bits of those? With such a minuscule pipe, the machinery at either end is by necessity going to be much greater than the volume of data passing through, so what's the difference between 25Mb of code, and 1Mb of code and 24Mb of image data?

(note the original guidelines ruled out restricting the input to images already in the library - I'm not suggesting that).






compression