从任意字符串生成图像 [英] Generate an image from arbitrary strings

查看:265
本文介绍了从任意字符串生成图像的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我已经看到了很多ascii艺术转换器的图像,但我需要的是更复杂一点。而不是从ascii字符创建的马赛克图像,我需要能够使用任意长度的预定义字符串集作为我的马赛克图块。



我做得很好谷歌搜索,但我甚至不知道如何构建我的查询?有这样的事吗?如果它不会在其图像生成中使用重复项,则可获得奖励。

解决方案

不太适合Stack Overflow,但仍然是一个有趣的项目。所以我有一点乐趣,看看我能走多远。



我认为归结为:


  1. 计算一组ASCII字符的灰度值;

  2. 计算每个字符串的最佳拟合;

  3. 重复2.直到完成。

我不认为没有重复是可行的,除非你有非常小的图像和很多候选字符串。这就是我想出来的,使用我的头像和我当前的徽章作为字符串列表。 (我排除了我的c徽章;不知何故,我的程序决定对大补丁来说最适合,这不是很有吸引力。精神注释:不包括单字符串。)



'预类= 朗 - 无prettyprint-越权> QuorumQuorumAutobiographerQuorumQuorumQuorumJongwareQuorumQuorumQuorumQuorumQuor
umQuorumQuorumAutobiographerQuorumQuorumSupporterQuorumQuorumProofreaderQuorumQu
orumQuorumAutobiographerQuorumQuorumQuorumQuorumQuorumQuorumAutobiographerQuorum
QuorumQuorumAutobiographerQuorumQuorumQuorumQuorumQuorumQuorumAutobiographerQuor
umQuorumQuorumAutobiographerQuorumQuorumQuorumAutobiographerQuorumMortarboardQuo
rumQuorumAutobiographerQuorumQuorumQuorumQuorumAutobiographerQuorumMortarboardQu
orumQuorumAutobiographerQuorumQuorumQuorumQuorumJongwareQuorumQuorumCommentator Q
uorumQuorumAutobiographerQuorumQuorumQuorumQuorumQuorumQuorumQuorumAutobiographe
rQuorumQuorumAutobiographerQuorumQuorumProofreaderJongwareQuorumQ uorumQuorumQuor
umQuorumQuorumMortarboardJongwareQuorumProofreaderCommentatorSuffrageQuorumQuoru
mQuorumQuorumJongwareQuorumAutobiographerSuffrageCommentatorCaucusCriticCleanupQ
uorumQuorumMortarboardAutobiographerCommentatorQuorumConstituentCriticCriticQuor
umQuorumQuorumQuorumAutobiographerJongwareCleanupSupporterInvestorCriticCleanupQ
uorumQuorumQuorumQuorumAutobiographerFanaticCleanupFanaticInvestorCriticCleanupQ
uorumQuorumQuorumQuorumAutobiographerCriticInformedSupporterCriticCriticInformed
QuorumQuorumQuorumQuorumAutobiographerCriticQuorumSupporterInvestorFanaticQuorum
QuorumQuorumQuorumQuorumAutobiographerCriticCleanupCommentatorQuorumDeputyQuorum
QuorumQuorumQuorumQuorumAutobiographerCriticInvestorCaucusInformedDeputyQuorumQu
orumQuorumQuorumQuorumQuorumCommentatorCriticCriticCitizen PatrolQuorumQuorumQuo
rumQuorumQuorumQuorumQuorumAutobiographerCriticCriticCitizen PatrolQuorumQuorumQ
uorumQuorumQuorumQuorumQuorumAuto biographerCriticCriticCitizen PatrolStewardQuor
umQuorumQuorumQuorumQuorumAutobiographerConstituentCitizen PatrolCaucusQuorumQuo
rumQuorumQuorumQuorumQuorumAutobiographerInvestorCriticConstituentQuorumQuorumQu
orumQuorumQuorumQuorumQuorumCommentatorConstituentCleanupCaucusCleanupQuorumQuor
umQuorumQuorumQuorumQuorumAutobiographerInvestorCleanupSupporterInformedQuorumQu
orumQuorumQuorumAutobiographerCommentatorCriticInformedJongwareJongwareQuorumQuo
rumQuorumQuorumAutobiographerCommentatorCriticInvestorJongwareJongwareQuorumQuor
umQuorumQuorumAutobiographerFanaticInvestorCriticInformedCleanupQuorumQuorumQuor
umQuorumQuorumQuorumDeputySupporterInvestorConstituentCaucusQuorumQuorumQuorumQu
orumQuorumQuorumAutobiographerCriticInvestorCriticSupporterQuorumQuorumQuorumQuo
rumQuorumQuorumQuorumAutobiographerInvestorInvestorCleanupQuorumQuorumQuorumQuor
umQuorumQuorumQuorumQuorumCommentatorInvestorInvestorQuorumQuorumQuorumQuorumQuo
r umQuorumQuorumQuorumQuorumCommentatorInvestorInvestorQuorumQuorumQuorumQuorumQu
orumQuorumQuorumQuorumQuorumCommentatorInvestorCleanupStewardQuorumQuorumQuorumQ
uorumQuorumQuorumQuorumQuorumCommentatorInvestorJongwareQuorumQuorumQuorumQuorum
QuorumQuorumQuorumQuorumQuorumAutobiographerCleanupQuorumQuorumQuorumQuorumQuoru
mQuorumQuorumQuorumQuorumQuorumAutobiographerSuffrageQuorumQuorumQuorumQuorumQuo
rumQuorumQuorumQuorumQuorumQuorumAutobiographerDeputyQuorumQuorumQuorumQuorumQuo
rumQuorumQuorumQuorumQuorumQuorumQuorumAutobiographerQuorumQuorumQuorumQuorumQuo
rumQuorumQuorumQuorumQuorumQuorumQuorumQuorumQuorumQuorumQuorumQuorumQuorumQuoru

你必须眯一点;在小尺寸看起来像这样:





以下是我创建它的方法。



步骤1:找到合适的图像;



第2步:转换为灰度;



第3步:将灰色转换为极值。此步骤是为了确保输入范围(灰度值)使用0到255的整个范围。



步骤4:调整图像大小以获得最佳效果。我选择了80x40,故意将图像压缩了一半。这是因为文本通常高于宽度。不同的字体需要不同的宽高比! 80 将是每行的字符数, 40 是总行数。



我使用Photoshop进行上述步骤,只是因为我不想为它编写代码。只要您可以访问原始图像数据,这并不困难或者其他什么,但这是很多工作而且不是很有趣。



中间步骤,放大400%所以你可以看到像素:





步骤5:找到一个等宽的位图字体。我在网上找到了一个漂亮的8x8。也许更大的可能更好,但只是非常小,因为限制因素是你的字符串,而不是字体。



步骤6:计算每个ASCII字符的灰色值。这是黑色像素的数量除以像素的总数。为了更好的传播,我将每个字符的结果除以找到的最大值,因此最低值为 0 (对于空格),最高值为 1 (恰好是 M ,但这取决于字体)。然后我将这些值乘以255,因此它模仿灰度值。最后,由于这些值与灰度图像中的值相反,我将其替换为 255-value



在我之间进行了大量测试,以确保我的初步想法仍然合理。这是我的测试图像的转储,使用简单的灰色到字符转换:

  0MMMMMM00000000000RDRRDDDDDDDDDDDDDR #@ RRRRR#00000RRR @ RRRRR @ RR @ RRRRD和放大器; 44放大器;#00#0000 
MMMMMM000000000000RDRDDDDDDDDDDDDDDDR0 #### 0R&功放;&安培;&安培;&安培;&安培;&安培; DR @ RRR @ ####### ## RRDDD4 @ 0000000
MMM000#00000000000RDRRDDDDDDDDDDD&安培;&安培;&安培; R00#000 @&安培; DR @ #### RR @#0000000 ## 0#RD4PP&安培; R @ 00000
M000#0000000000000RDDDDDDDDDDD&安培; D& D& R ### 0000 @#0000#@@ ## @@@@@## 000000R& 2FPP4R#000
00 ### 0000000000000RDDDDDDDDDDDDD&&& D0000#@ ## @ ## 00 ## @ RDD&安培; DRRRR#00000 @ R4FFP4PD @ 00
00#000000000000000RDDDDDDDDDD&安培; d&安培; d&安培;&安培;&安培; DRRRRDR @@@ ## 00#的R& 4&安培; 44DDDRRR#0000 ##的R& ; FPP4PRR @
00 ## 00#00000000000RDDDDDDDDDD&&&&&& RDRRRRRRRR ## @@ RR& F4& RDDRR @@#0000000#& 44&& 4FD
000000000000000000DDDDDDD&安培;&安培;&安培; DD&安培;&安培;&安培; d&安培;&安培; R ## @ RRRRRRRRRRRRD&安培; DR D& 44DD& RR @#00000RDDRR4F4
000000000000000000RDDDDDDDRRDRDDD& DR @ ### @ R& 4& 4444PP4DRRR& P22FF2FP& DRRRRRRRR @ R4FD
000000000000000000RRRRRRR @ 00 @@ R&& DRRRRRR @& P2 $ 33 * 33 * 4RRRDP23 $ * 33 $$ ** 333 * $$ 2D#@ 4DR
000000000000000000RRRRRRR @ 0000 #DDRRRRRD& D4 * $$ %% ff3F& DRRR2 $ 1%$$%11ff%ll1l;'IRDF& R
000000000000000000RRR @#0#00000R4444DRRRR& 3llf33 $ 32PDRR& 3Ii(i%fIlI1Il!ii /'。FF4DR
0000000#0000000000#@@#0MM0M00#RP22 * 24DR4 $ l !!! I%* P4DDP31i === / lf1Illi((ii =; .. * F4RR
000000000000000000#@@ ## 0M00000 @ F * $%* 2PFflilllI1f3 * 2PF3fIi / =(lf $ fIi / ======; iF& ; P4R
000000000000000000 ## @ ## 00000000& 3f $ 2F2 * 1i!ll1 $ 2P4RD& 4P * $$%!ii!I!ii / = / = ;;;(*& R4FR
000000000000000000 ##### 00000000D%I3 $$ fflil!l1 $ 3%3& RD2PP * $%1ll!lI1%f $ 3fI =1RRRRDR
000000000000000000 ##### 00000000Rf1f%II1IIl!l !! !! 1%ff $ * FFFF *%((lf ** F4&​​amp; D& PPFf2RRRRRR
00000000000000000M ##### 0000000003!i11II11l !!!(ilIIl1f $ f%I == 1FP4& @#R& DP22& amp; ; RRR @#@
000000 0000000000000 ### 0000000000#$ i / iIIIl !! i =;; ===;; i12FFP4& 4 * 4& * FRRRR @@ R
000000000000000000M000000000000000R4FF1l!i(=; '''...'; / i $ 3 $ f $$ 33 $$$ 4DRRRRRR $ b $ 00 000000000000000000000000000M00000000 @ 21l(/ ii / = ;; = ilI;'...'=; I %11f $$$ ffP @@ RR @ R#0
000000000000000000000000000M00000000& 11!= / li(i!I %% Ii; ...。;!我!! I1ff $ * R0#@# 0000
000000000000000000000000M0000M000000 $ lli = // = / i!lIi / l%I /= //'= Iiiil%f $ PR @#@ 00000
000000000000000000000000M0M0M00000MRl !!! / = ;; / / l%fl!lI%3233 $ ff%11II %% f * 2PP @ ## 00000
00000000000000000M000000M0MM00000003 = illl !! iI%11 %% f%f $ 32FF22 $ 1%ff $ f2DD4PR0000000
00000000000000000M00M0# RRRRRRRRRRRPi /(lllI1I(=; = iI $ 2222FPFFP * $ fff%FRR2322& R00000
00000000000000000MM00#RRD&&&&& 444 * l /(i!ll!i!== /(il %$ 33 * 2FFF23 $ ff * 4DDDF33 * 22& 0000
0000000000000000000000 @ R @@@@@#& amp; f!((/ i !!! lI!i = ;; /!l1f32 * 3 $$$ ff $ 2& RR @ ### @ ## 00 ## 000
0000000000000000#RRRR @@ 4F4R0R3!////(iii !! l%Ii =;= l%f $ 333 $ ff%$ 4 ############ 00000#
0000000000000000000000#@@@#0Di / ii(= /(i !!! lI %% 1!(iI%$ ** $$ fffF @ 0000000000000000000
00000000000000000000000000000R3l((/((ii!lll!I%) $ 3 $ f $$$$$ 3 $ f20M0000000000000000000
000000000000000000000000000000#2l ///((!! l !! i !! 1%f%f $ 3 $ f %% fR000000000000000000000
00000000000000#00000000000000000& l //(我llllII1 %%% 1I1ff1I1和放大器;!000000000000000000#00#
M00000000000000000000000000000000R3l!llII111 %%%%%%˚F$$ F%2000000000000000000RR00#
0000#000000000000000000000000000000R *%1II111 %% FFFF $ 33 fffR000000000000000000 ## 00#
0 #### 000000000000000000000000000000M0RF3ff $$$ fff $$ 33 $ ff& 00000000000#000000 ## 000R
#00000000#00000000000000000000000000000R4FFFF22 ***** 3fF00000000000000000000000 @&
00 ### 000000000000000000000000000000000000 @ RRDD&安培;&安培;&安培; 4P * 34#00000000000000000000000# - [R
00000 #### 000000000000000000000000000000000000 ## @ RRDDR00000000000000M0000000000 ##
00000000#000000000000000000000000000000000000000000000000000000000000000000000 ##

这类似于您的平均图像到ASCII艺术转换器的输出。



步骤7:找到自己要使用的字符串列表。



步骤8:从左上角开始,测试每个字符串的覆盖范围反对形象。打印出最佳配合,按字符串的长度增加位置,重复直到完成。 (如果您不想重复,则此时从池中删除字符串。)



步骤9:获利!






对于覆盖测试,我为每个字符/像素使用了(source-dest)²的总和,除以字符串的长度:lower = better - 字符串和目标之间的最小差异。



我在这里没有考虑漂亮的行结尾。如果一个单词准确地填充了一行,我尝试给出一个负面的奖励,但是输出的差异很小。它可能仍然适用于更大的字符串集。



可能的改进是测试字符串的序列,即代替贪婪这里采用动态编程方法,就像唐纳德·克努特(Donald Knuth)设计的那样,决定自动换行文本中的最佳休息时间。


I've seen plenty of image to ascii art converters, but what I need is a little more complex. Instead of a mosaic image created from ascii chars I need to be able to use a predefined set of strings of arbitrary lengths as my mosaic tiles.

I've done a good bit of Googling, but Im not even sure how to structure my query? Does anything like this exist? And bonus if it wont use duplicates in its image generation.

解决方案

Not really suitable for Stack Overflow, but an interesting project nevertheless. So I had a go at it for a bit of fun and see how far I could get.

I think it comes down to this:

  1. calculate a gray value for a set of ASCII characters;
  2. calculate the 'best fit' for each string;
  3. repeat 2. until done.

I don't think "without duplicates" is feasible, unless you have very small images and lots of candidate strings. This is what I came up with, using my avatar and my current badges as list of strings. (I excluded my "c" badge; somehow my program decided that was the 'best fit' for large patches, which wasn't very attractive. Mental note: Do Not Include 1-Character Strings.)

QuorumQuorumAutobiographerQuorumQuorumQuorumJongwareQuorumQuorumQuorumQuorumQuor
umQuorumQuorumAutobiographerQuorumQuorumSupporterQuorumQuorumProofreaderQuorumQu
orumQuorumAutobiographerQuorumQuorumQuorumQuorumQuorumQuorumAutobiographerQuorum
QuorumQuorumAutobiographerQuorumQuorumQuorumQuorumQuorumQuorumAutobiographerQuor
umQuorumQuorumAutobiographerQuorumQuorumQuorumAutobiographerQuorumMortarboardQuo
rumQuorumAutobiographerQuorumQuorumQuorumQuorumAutobiographerQuorumMortarboardQu
orumQuorumAutobiographerQuorumQuorumQuorumQuorumJongwareQuorumQuorumCommentatorQ
uorumQuorumAutobiographerQuorumQuorumQuorumQuorumQuorumQuorumQuorumAutobiographe
rQuorumQuorumAutobiographerQuorumQuorumProofreaderJongwareQuorumQuorumQuorumQuor
umQuorumQuorumMortarboardJongwareQuorumProofreaderCommentatorSuffrageQuorumQuoru
mQuorumQuorumJongwareQuorumAutobiographerSuffrageCommentatorCaucusCriticCleanupQ
uorumQuorumMortarboardAutobiographerCommentatorQuorumConstituentCriticCriticQuor
umQuorumQuorumQuorumAutobiographerJongwareCleanupSupporterInvestorCriticCleanupQ
uorumQuorumQuorumQuorumAutobiographerFanaticCleanupFanaticInvestorCriticCleanupQ
uorumQuorumQuorumQuorumAutobiographerCriticInformedSupporterCriticCriticInformed
QuorumQuorumQuorumQuorumAutobiographerCriticQuorumSupporterInvestorFanaticQuorum
QuorumQuorumQuorumQuorumAutobiographerCriticCleanupCommentatorQuorumDeputyQuorum
QuorumQuorumQuorumQuorumAutobiographerCriticInvestorCaucusInformedDeputyQuorumQu
orumQuorumQuorumQuorumQuorumCommentatorCriticCriticCitizen PatrolQuorumQuorumQuo
rumQuorumQuorumQuorumQuorumAutobiographerCriticCriticCitizen PatrolQuorumQuorumQ
uorumQuorumQuorumQuorumQuorumAutobiographerCriticCriticCitizen PatrolStewardQuor
umQuorumQuorumQuorumQuorumAutobiographerConstituentCitizen PatrolCaucusQuorumQuo
rumQuorumQuorumQuorumQuorumAutobiographerInvestorCriticConstituentQuorumQuorumQu
orumQuorumQuorumQuorumQuorumCommentatorConstituentCleanupCaucusCleanupQuorumQuor
umQuorumQuorumQuorumQuorumAutobiographerInvestorCleanupSupporterInformedQuorumQu
orumQuorumQuorumAutobiographerCommentatorCriticInformedJongwareJongwareQuorumQuo
rumQuorumQuorumAutobiographerCommentatorCriticInvestorJongwareJongwareQuorumQuor
umQuorumQuorumAutobiographerFanaticInvestorCriticInformedCleanupQuorumQuorumQuor
umQuorumQuorumQuorumDeputySupporterInvestorConstituentCaucusQuorumQuorumQuorumQu
orumQuorumQuorumAutobiographerCriticInvestorCriticSupporterQuorumQuorumQuorumQuo
rumQuorumQuorumQuorumAutobiographerInvestorInvestorCleanupQuorumQuorumQuorumQuor
umQuorumQuorumQuorumQuorumCommentatorInvestorInvestorQuorumQuorumQuorumQuorumQuo
rumQuorumQuorumQuorumQuorumCommentatorInvestorInvestorQuorumQuorumQuorumQuorumQu
orumQuorumQuorumQuorumQuorumCommentatorInvestorCleanupStewardQuorumQuorumQuorumQ
uorumQuorumQuorumQuorumQuorumCommentatorInvestorJongwareQuorumQuorumQuorumQuorum
QuorumQuorumQuorumQuorumQuorumAutobiographerCleanupQuorumQuorumQuorumQuorumQuoru
mQuorumQuorumQuorumQuorumQuorumAutobiographerSuffrageQuorumQuorumQuorumQuorumQuo
rumQuorumQuorumQuorumQuorumQuorumAutobiographerDeputyQuorumQuorumQuorumQuorumQuo
rumQuorumQuorumQuorumQuorumQuorumQuorumAutobiographerQuorumQuorumQuorumQuorumQuo
rumQuorumQuorumQuorumQuorumQuorumQuorumQuorumQuorumQuorumQuorumQuorumQuorumQuoru

You have to squint a bit; at a small size it looks like this:

Here is how I created it.

Step 1: Find a suitable image;

Step 2: convert to grayscale;

Step 3: convert gray to extremes. This step is to ensure the input range (gray values) uses the full range of 0 to 255.

Step 4: resize the image for a best fit. I chose 80x40, and deliberately squashed the image by half. This because 'text' usually is higher than it is wide. Different fonts need different aspect ratios! The 80 is going to be the number of characters per line, the 40 is total number of lines.

I used Photoshop for the above steps, just because I did not want to write code for it. It's not hard or something, as long as you have access to the raw image data, but it's a lot of work and not interesting.

Intermediate step, enlarged by 400% so you can see the pixels:

Step 5: Find yourself a monospaced bitmap font. I found a nice 8x8 one somewhere on the 'web. Perhaps a larger size may work better, but only very minor, because the limiting factor is your strings, not the font.

Step 6: Calculate 'gray' values for each of the ASCII characters. This is the number of black pixels, divided by the total number of pixels. For a better spread, I divided the result for each character by the maximum found, so the lowest value is 0 (for space) and the highest is 1 (which happened to be for M, but it depends on the font). I then multiplied the values by 255, so it mimics grayscale values. Finally, as these values were the reverse of those in a grayscale image, I replaced them with 255-value.

In between I did a lot of testing to make sure my initial idea was still sound. Here is a dump of my test image using a plain gray-to-character translation:

0MMMMMM00000000000RDRRDDDDDDDDDDDDDDR#@RRRRR#00000RRR@RRRRR@RR@RRRRD&44&#00#0000
MMMMMM000000000000RDRDDDDDDDDDDDDDDDR0####0R&&&&&&DR@RRR@#########RRDDD4@0000000
MMM000#00000000000RDRRDDDDDDDDDDD&&&R00#000@&DR@####RR@#0000000##0#RD4PP&R@00000
M000#0000000000000RDDDDDDDDDDD&D&&D&R###0000@#0000#@@##@@@@@##000000R&2FPP4R#000
00###0000000000000RDDDDDDDDDDDDDD&&&D0000#@##@##00##@RDD&DRRRR#00000@R4FFP4PD@00
00#000000000000000RDDDDDDDDDD&D&D&&&DRRRRDR@@@##00#R&4&44DDDRRR#0000##R&FPP4PRR@
00##00#00000000000RDDDDDDDDDDD&&&&&&RDRRRRRRRR##@@RR&F4&RDDRR@@#0000000#&44&&4FD
000000000000000000DDDDDDD&&&DD&&&D&&R##@RRRRRRRRRRRRD&DRD&44DD&RR@#00000RDDRR4F4
000000000000000000RDDDDDDDRRDRDDD&DR@###@R&4&4444PP4DRRR&P22FF2FP&DRRRRRRRR@R4FD
000000000000000000RRRRRRR@00@@R&&DRRRRRR@&P2$33*33*4RRRDP23$*33$$**333*$$2D#@4DR
000000000000000000RRRRRRR@0000#DDRRRRRD&D4*$$%%ff3F&DRRR2$1%$$%11ff%ll1l;'IRDF&R
000000000000000000RRR@#0#00000R4444DRRRR&3llf33$32PDRR&3Ii(i%fIlI1Il!ii/' .FF4DR
0000000#0000000000#@@#0MM0M00#RP22*24DR4$l!!!I%*P4DDP31i===/lf1Illi((ii=;..*F4RR
000000000000000000#@@##0M00000@F*$%*2PFflilllI1f3*2PF3fIi/=(lf$fIi/======;iF&P4R
000000000000000000##@##00000000&3f$2F2*1i!ll1$2P4RD&4P*$$%!ii!I!ii/=/=;;;(*&R4FR
000000000000000000#####00000000D%I3$$fflil!l1$3%3&RD2PP*$%1ll!lI1%f$3fI="1RRRRDR
000000000000000000#####00000000Rf1f%II1IIl!l!!1%ff$*FFFF*%((lf**F4&D&PPFf2RRRRRR
00000000000000000M#####0000000003!i11II11l!!!(ilIIl1f$f%I="=1FP4&@#R&DP22&RRR@#@
0000000000000000000###0000000000#$i/iIIIl!!i=;"";===;""""";i12FFP4&4*4&*FRRRR@@R
000000000000000000M000000000000000R4FF1l!i(=;"''"""""'...';/i$3$f$$33$$$4DRRRRRR
000000000000000000000000000M00000000@21l(/ii/=;;=ilI;"'...'=;I%11f$$$ffP@@RR@R#0
000000000000000000000000000M00000000&11!=/li(i!I%%Ii;... .";"!I!!I1ff$*R0#@#0000
000000000000000000000000M0000M000000$lli=//=/i!lIi/l%I/""=//'=Iiiil%f$PR@#@00000
000000000000000000000000M0M0M00000MRl!!!/=;;/l%fl!lI%3233$ff%11II%%f*2PP@##00000
00000000000000000M000000M0MM00000003=illl!!iI%11%%f%f$32FF22$1%ff$f2DD4PR0000000
00000000000000000M00M0#RRRRRRRRRRRPi/(lllI1I(=;=iI$2222FPFFP*$fff%FRR2322&R00000
00000000000000000MM00#RRD&&&&&444*l/(i!ll!i!==/(il%$33*2FFF23$ff*4DDDF33*22&0000
0000000000000000000000@R@@@@@#&f!((/i!!!lI!i=;;/!l1f32*3$$$ff$2&RR@###@##00##000
0000000000000000#RRRR@@4F4R0R3!////(iii!!l%Ii=;"=l%f$333$ff%$4############00000#
0000000000000000000000#@@@#0Di/ii(=/(i!!!lI%%1!(iI%$**$$fffF@0000000000000000000
00000000000000000000000000000R3l((/((ii!lll!I%$3$f$$$$$3$f20M0000000000000000000
000000000000000000000000000000#2l///((!!l!!i!!1%f%f$3$f%%fR000000000000000000000
00000000000000#00000000000000000&l//(i!llllII1%%%1I1ff1I1&000000000000000000#00#
M00000000000000000000000000000000R3l!!llII111%%%%%%f$$f%2000000000000000000RR00#
0000#000000000000000000000000000000R*%1II111%%ffff$33fffR000000000000000000##00#
0####000000000000000000000000000000M0RF3ff$$$fff$$33$ff&00000000000#000000##000R
#00000000#00000000000000000000000000000R4FFFF22*****3fF00000000000000000000000@&
00###000000000000000000000000000000000000@RRDD&&&4P*34#00000000000000000000000#R
00000####000000000000000000000000000000000000##@RRDDR00000000000000M0000000000##
00000000#000000000000000000000000000000000000000000000000000000000000000000000##

This is similar to what your average image to ASCII art converter outputs.

Step 7: find yourself a list of strings to use.

Step 8: starting at the top left, test the coverage of each of your strings against the image. Print out the best fit, increase the position by this strings' length, repeat until done. (If you want no duplicates, you remove the string from your pool at this point.)

Step 9: profit!


For the coverage test, I used the sum of (source - dest)² for each character/pixel, divided by the length of the string: lower = better -- the smallest difference between the string and the destination.

I did not consider pretty line endings here. I experimented with giving a negative bonus if a word filled a line exactly, but the difference in output was minor. It may still work with a larger set of strings.

A possible improvement is to test a sequence of strings, i.e., instead of the greedy approach here, use a dynamic programming approach, much like Donald Knuth devised to decide the best breaks in word wrapping text.

这篇关于从任意字符串生成图像的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆