小聪明图片消失在另一张图片里(代码片段)

小鱼吻水 小鱼吻水     2022-10-30     666

关键词:

概要

 

偶然看到一篇文章伪·黑科技】基于像素微调实现的文字隐写术,受此启发,能把文字转成二进制,那么图片像素转成二进制岂不更容易,于是我就写了一个隐藏图片的代码,也就有了这篇随笔。

但是刚写出来不完美,有几点需要改进的地方,现在还没有想通,做此记录,以后有机会再慢慢改进:

  • python 包 matplotlib 保存数组构成的图片时,会自动加个透明层,即不是我想要的 RGB 格式,而是 RGBA 格式。why,why,不得不转向其它包
  • 包存图片格式时,一般的数组有可能格式不对,如果遇到错误,就保存为 unit8 格式

 


效果图

 

提示:这是我截的图,不是原图,像素可能不满足要求,做实验可用自己的图片

图 1:要被隐藏的图片

图 2:隐藏之后的图片效果图


代码

 

基本的原理就是利用二进制微调宿主像素。代码中的解释已经很清楚了,在此不再多述。

# -*- coding: utf-8 -*-
"""
Created on Thu Mar 29 11:47:43 2018

@author: zhoukui
"""
import numpy as np
from PIL import Image
import matplotlib.image as mpimg

import sys

def image2Bin(imageFile):
    image = mpimg.imread(imageFile)
    imageArr = image.ravel()
    
    binList = list((map(bin,imageArr)))
    
    for i, item in enumerate(binList):  # 把数字全部转换为 8 位的 0 1 数据 
        binList[i] = item[2:]  # 把二进制标志 \'0b\' 去掉
        binList[i] = \'0\'*(8 - len(binList[i])) + binList[i]
    
    pixes_x, pixes_y, _ = image.shape # 把原始图片像素保存一下
    
    binX = bin(pixes_x)[2:]
    binY = bin(pixes_y)[2:]
    binList.insert(0,\'0\'*(16-len(binX)) + binX)
    binList.insert(1,\'0\'*(16-len(binY)) + binY)
    # 前两个 16 位表示的是像素长宽,像素长宽相乘再乘以 3 得到后面 8 位的数目
    return binList  

def showImage(imageArr, imageTitle):
    
    im = Image.fromarray(imageArr)
    im.save(imageTitle)
    im.show()
    

    
def oneHide(pix, pixValue):
    if pix == \'0\':  # 使图片像素变为偶数
         if pixValue == 255:
              pixValue = 244
         elif pixValue % 2 == 1:
              pixValue += 1 
    elif pixValue % 2 == 0:
         pixValue += 1
    
    return pixValue  # 返回去改变这像素值     

def hiding(binList, hidingImageFile):
    image = mpimg.imread(hidingImageFile)
    #print(image.shape)
    imageArr = image.ravel()
    
    # 每一个像素隐藏一个 0 或者 1
    # 判断是否藏得下
    if (len(binList)*8+16 > len(imageArr)):
        print("藏不下,换一张宿主更大的图片或把要藏的图片调小")
    else:
        flag = 0  # 标记藏到哪了
        # 先藏前两个 16 位的
        for i in range(2):
            for j in range(16):
                imageArr[flag] = oneHide(binList[i][j], imageArr[flag])
                flag += 1
        
        # 然后藏剩下的
        for _, item in enumerate(binList[2:]): 
            if flag % 8640 == 0:
                sys.stdout.write(\'\\r complete percent ----->:%.0f%%\' % (flag/82976.))                
            for j in range(8):
                imageArr[flag] = oneHide(item[j], imageArr[flag])
                flag += 1
        
        sys.stdout.flush()  
    #print(imageArr[:8])
    imageArr = imageArr.reshape(image.shape)  #.astype(np.uint8) 
    
    return imageArr      

def imerging(imageFile):
    image = mpimg.imread(imageFile)  # 这种读取图片直接是 Ndarray
    
    imageArr = image.ravel()
    
    # 先把隐藏图片的大小解析出来
    tempList = [str(i % 2) for i in imageArr[:32]] 
    
    pixesX = int(\'\'.join(tempList[:16]), 2)
    pixesY = int(\'\'.join(tempList[16:]), 2)
    #print(pixesX, pixesY)
    
    # 把隐藏图片的像素解析出来
    temp2List = [str(i % 2) for i in imageArr[32 : 32 + pixesX*pixesY*3*8]]
    
    tempArr = np.zeros(pixesX*pixesY*3,)

    for i in range(pixesX*pixesY*3):
        
        tempArr[i] = int(\'\'.join(temp2List[8*i:8*(i+1)]), 2)
    
    #sys.stdout.flush() 
    
    tempArr = tempArr.reshape(pixesX, pixesY, 3).astype(np.uint8) # 不加会模糊   
    showImage(tempArr, "image_after_decreption.bmp") 

                
def imageEncre(hidedImageFile, hidingImageFile):
    # 可视化隐藏前图片
    #imageArrBefore = mpimg.imread(hidingImageFile)
    #showImage(imageArrBefore, "image before hiding")
    
    # 把要加密的图片转换成 0  1 数字
    print("加密前准备工作...")
    binList = image2Bin(hidedImageFile) 
    
    # 接下来把 0 与 1 藏进另一张图片
    print("开始加密...")
    imageArrAfter = hiding(binList, hidingImageFile)
    #print(imageArrAfter[:8,:,:])
    showImage(imageArrAfter, "image_after_encreption.bmp")

def imageDecre(imageFile):
    print("解码中...")
    imerging(imageFile)
    
    
if __name__ == "__main__":  
    #imageEncre("hided.jpg", "hiding.jpg") 
    imageDecre("image_after_encreption.bmp")

Delphi 在另一张图片上绘制 png 文件的一部分

】Delphi在另一张图片上绘制png文件的一部分【英文标题】:Delphidrawingpartofpngfileonanotherimage【发布时间】:2021-05-1703:26:39【问题描述】:我正在使用此函数在特定位置的TImage上绘制png:procedureTForm1.PlacePNG(nam:string;px,py:Integer);varvPic:... 查看详情

java重叠两个视图,使一张图在另一张图的上面。(代码片段)

查看详情

xml重叠两个视图,使一张图在另一张图的上面。(代码片段)

查看详情

xml重叠两个视图,使一张图在另一张图的上面。(代码片段)

查看详情

[从一个单元格获取值,并将其聚焦在另一张表上,vbaexcel(代码片段)

我需要在另一张纸上搜索一个元素,我认为我以某种方式应用了错误的方法,因此无法激活单元格并集中该元素。我在执行代码时没有收到任何错误我留下插图的照片,以免我的想法和所使用的代码一起被很好地理解IfTarget.Count=... 查看详情

鼠标经过图片,图片翻转显示另一张图片

当鼠标移入外层的div盒子子时,图片会翻转180度,并且显示图片的背面(即第二张图片)。效果如下:  代码:<!DOCTYPEhtml><html> <head> <metacharset="UTF-8"> <title></title> </head> <body> < 查看详情

ctfshow做题misc入门模块11-20(代码片段)

...;但是无果。用010editor打开,运行模板png.bit,看到图片有两个IDAT块。(前面一题misc10也有两个IDAT块)这题需要删除第一个IDAT块,涉及一 查看详情

我要在一个网页上传一张图片到服务器,然后保存图片的地址,在另一个页面显示图片

我用的是struts,在页面上传图片后,Action里得到了这个图片文件File,然后我想将图片保存到服务器的一个文件夹里,并将地址保存在数据库里,这样需要在网页上显示的时候就直接写上地址就行了。问题是:我写ServletActionContext... 查看详情

如何用ps从一张图片上截取一个矩形区域到另一张图片上

在图片一是要矩形选框工具框选图片,ctrl+J键复制一层,在图层面板上右键点击该图层,现在复制图层,在弹窗中选择图片二,点确定,你再回到图片二你要的图片就出现了。参考技术A用矩形选区工具框取想截取的部分,复制... 查看详情

java示例代码_在我的表格里放一张图片

java示例代码_在我的表格里放一张图片 查看详情

CSS 将一张图片放在另一张图片之上

】CSS将一张图片放在另一张图片之上【英文标题】:CSSplacingoneimageontopofanother【发布时间】:2013-08-1615:22:04【问题描述】:我正在开发CSS设计模板。我有两张图片imageOne和imageTwo。两者都是position:relative,因为如果我将其中一个设... 查看详情

atitit判断判断一张图片是否包含另一张小图片

 Atitit判断判断一张图片是否包含另一张小图片  1.keyword12. 模板匹配是在图像中寻找目标的方法之一(切割+图像相似度计算)13.匹配效果24.图片相似度的算法(感知哈希算法”(Perceptualhashalgorithm)25.性能结果26... 查看详情

当鼠标悬停在没有css的标题上时,如何使缩略图消失?

...时间】:2013-09-2510:07:08【问题描述】:当我将鼠标悬停在图片的div上时,我有一个简单的jQuery代码,通过隐藏一张图片并显示另一张图片来更改帖子的缩略图。当我将鼠标悬停在.thumbs类中标记的 查看详情

phpwordpress获得第一张图片(代码片段)

查看详情

安卓xml布局,textview怎样设置背景,这个背景是两个图片,是png的。一张图片作为底,另一张叠加

这需要在drawable文件中写一个xml里面用LayerList放两张图片,textView使用图片是引用drawable中的xml就行了。。。参考技术Aandroid:background="@drawable/图片名称"就是设置控件背景的 查看详情

css3翻转图片问题

...ansform:rotateY(180deg);</style>代码在这,现在可以实现图片翻转效果,想问一下加什么代码可以实现翻转过去是另一张图片,也就是说翻转90度以后第一张图片应该是消失的,然后另一张图片继续展开到结束其实这个效果就是... 查看详情

我想用php将一张图片合成到另一张图片上去,但是要倾斜一定角度,像下面图片中的这样,高手帮忙啊

我要把另一张图片放在画红线的那个区域1L方法太先进了--使用PHP的GD库应该可以得到LZ想要的效果,这里给思路吧,具体代码需完善不少方面,实在没时间研究啊--//------------------------------------------------------------------------------------... 查看详情

python实现将一张图片裁剪多张(代码片段)

文章目录一、需求二、代码一、需求需要将一张图片,从中间对半裁剪为两张图片如:裁剪为两张:二、代码importosfromPILimportImageIMAGES_PATH='img\\\\test\\\\'#图片集地址#支持的格式IMAGES_FORMAT=['.png','.jp... 查看详情