복붙노트

[PYTHON] 파이썬에서 하프 톤 이미지

PYTHON

파이썬에서 하프 톤 이미지

저는 CYMK 이미지에서 각 색상을 분리하고 특수 하프 톤 프린터에 인쇄 될 하프 톤 이미지를 생성해야하는 프로젝트를 진행하고 있습니다. 사용 된 방법은 프로세스가 거의 동일하다는 점에서 실크 스크리닝과 유사합니다. 사진을 가지고 각 색상 채널을 탈피하십시오. 그런 다음 하프 톤을위한 화면을 만듭니다. 각 컬러 화면의 화면은 15-45도 (조절 가능)로 기울어 져 있어야합니다. 도트 크기 및 LPI는 사용자가 구성 할 수있는 값으로부터 계산 되어야만 다른 효과를 얻을 수 있습니다. 내가 듣는이 과정은 실크 심사에 사용되지만 CYMK 중간 색조를 설명하는 정보는 찾을 수 없습니다. 나는 단색으로 줄이고 새로운 인쇄 스타일의 흑백 하프 톤 이미지를 생성하기에 충분합니다.

나는 내가 다음과 같이해야한다고 생각할 것이다. 1. 파일을 컬러 채널로 나눕니다. 2. 해당 채널에 대한 단색 하프 톤 이미지를 생성합니다. 3. 결과 하프 톤 이미지를 도수 * 채널 번호로 기울입니다. 이것이 올바른 접근 방법인지 아는 사람 있습니까?

누구든지 이것에 대한 기존의 파이썬 코드를 알고 있습니까? 아니면이 과정이나 알고리즘에 대한 좋은 설명이 있습니까?

해결법

  1. ==============================

    1.저는 스크린 인쇄 스튜디오 (상당히 작은 것이 었습니다)를 사용 했었습니다. 실제로 색상 분리 인쇄를 한 적이 없지만 원칙에 대해서는 상당히 익숙합니다. 이것은 내가 그것에 접근하는 방법이다.

    저는 스크린 인쇄 스튜디오 (상당히 작은 것이 었습니다)를 사용 했었습니다. 실제로 색상 분리 인쇄를 한 적이 없지만 원칙에 대해서는 상당히 익숙합니다. 이것은 내가 그것에 접근하는 방법이다.

    이제 색상으로 분리 된 이미지가 있습니다. 언급했듯이, 회전 단계는 도트 정렬 문제를 줄여 주므로 (모든 것을 망칠 것입니다) 모아레 패턴 효과와 같은 요소는 합리적으로 최소화됩니다.

    이것은 PIL을 사용하여 코딩하는 것이 매우 쉬워야합니다.

    업데이트 2 :

    나는 당신을 위해 이것을 할 몇 가지 빠른 코드를 작성했습니다, 그것은 또한 GCA 함수를 포함합니다 (아래에 설명) :

    import Image, ImageDraw, ImageStat
    
    def gcr(im, percentage):
        '''basic "Gray Component Replacement" function. Returns a CMYK image with 
           percentage gray component removed from the CMY channels and put in the
           K channel, ie. for percentage=100, (41, 100, 255, 0) >> (0, 59, 214, 41)'''
        cmyk_im = im.convert('CMYK')
        if not percentage:
            return cmyk_im
        cmyk_im = cmyk_im.split()
        cmyk = []
        for i in xrange(4):
            cmyk.append(cmyk_im[i].load())
        for x in xrange(im.size[0]):
            for y in xrange(im.size[1]):
                gray = min(cmyk[0][x,y], cmyk[1][x,y], cmyk[2][x,y]) * percentage / 100
                for i in xrange(3):
                    cmyk[i][x,y] = cmyk[i][x,y] - gray
                cmyk[3][x,y] = gray
        return Image.merge('CMYK', cmyk_im)
    
    def halftone(im, cmyk, sample, scale):
        '''Returns list of half-tone images for cmyk image. sample (pixels), 
           determines the sample box size from the original image. The maximum 
           output dot diameter is given by sample * scale (which is also the number 
           of possible dot sizes). So sample=1 will presevere the original image 
           resolution, but scale must be >1 to allow variation in dot size.'''
        cmyk = cmyk.split()
        dots = []
        angle = 0
        for channel in cmyk:
            channel = channel.rotate(angle, expand=1)
            size = channel.size[0]*scale, channel.size[1]*scale
            half_tone = Image.new('L', size)
            draw = ImageDraw.Draw(half_tone)
            for x in xrange(0, channel.size[0], sample):
                for y in xrange(0, channel.size[1], sample):
                    box = channel.crop((x, y, x + sample, y + sample))
                    stat = ImageStat.Stat(box)
                    diameter = (stat.mean[0] / 255)**0.5
                    edge = 0.5*(1-diameter)
                    x_pos, y_pos = (x+edge)*scale, (y+edge)*scale
                    box_edge = sample*diameter*scale
                    draw.ellipse((x_pos, y_pos, x_pos + box_edge, y_pos + box_edge), fill=255)
            half_tone = half_tone.rotate(-angle, expand=1)
            width_half, height_half = half_tone.size
            xx=(width_half-im.size[0]*scale) / 2
            yy=(height_half-im.size[1]*scale) / 2
            half_tone = half_tone.crop((xx, yy, xx + im.size[0]*scale, yy + im.size[1]*scale))
            dots.append(half_tone)
            angle += 15
        return dots
    
    im = Image.open("1_tree.jpg")
    
    cmyk = gcr(im, 0)
    dots = halftone(im, cmyk, 10, 1)
    im.show()
    new = Image.merge('CMYK', dots)
    new.show()
    

    그러면 다음과 같이 바뀝니다.

    이것을 (눈을 감고 모니터에서 멀리 떨어지십시오) :

    이미지 샘플링은 픽셀 단위로 할 수 있으므로 (최종 이미지에서 원본 이미지의 해상도 유지) 유의하십시오. 이 작업을 수행하려면 sample = 1로 설정하십시오.이 경우 가능한 많은 도트 크기가되도록 눈금을 더 큰 숫자로 설정해야합니다. 이렇게하면 출력 이미지 크기가 커집니다 (원래 이미지 크기 * 배율 ** 2이므로 조심하십시오!).

    기본적으로 RGB에서 CMYK로 변환 할 때 K 채널 (검정색 채널)은 비어 있습니다. K 채널이 필요한지 여부는 인쇄 프로세스에 따라 다릅니다. CMY의 중복, 잉크 절약, 건조 시간 개선, 잉크 흘림 감소 등보다 나은 검정색을 얻는 데는 여러 가지 이유가있을 수 있습니다. 어쨌든 회색 성분 대체 기능 GCA도 작성 했으므로 CMY 오버랩을 대체 할 K 채널의 백분율을 설정하십시오 (코드 주석에서 조금 더 설명합니다).

    설명 할 몇 가지 예가 있습니다. 샘플 = 1 및 스케일 = 8로 이미지에서 문자 F를 처리하므로 상당히 높은 해상도.

    백분율 = 0 인 4 개의 CMYK 채널, 비어있는 K 채널 :

    결합하여 생산 :

    CMYK 채널 (백분율 = 100)이므로 K 채널이 사용됩니다. 시안 색 채널이 완전히 억제 된 것을 볼 수 있으며, 마젠타 색 및 노란색 채널은 이미지 하단의 검은 색 영역에서 훨씬 적은 잉크를 사용합니다.

  2. ==============================

    2.내 솔루션은 PIL을 사용하지만 내부적으로 지원되는 내부 디더링 방법 (Floyd-Steinberg)을 사용합니다. 그래도 유물을 생성하므로 C 코드를 다시 작성하는 것을 고려하고 있습니다.

    내 솔루션은 PIL을 사용하지만 내부적으로 지원되는 내부 디더링 방법 (Floyd-Steinberg)을 사용합니다. 그래도 유물을 생성하므로 C 코드를 다시 작성하는 것을 고려하고 있습니다.

        from PIL import Image
    
        im  = Image.open('tree.jpg')             # open RGB image
        cmyk= im.convert('CMYK').split()         # RGB contone RGB to CMYK contone
        c = cmyk[0].convert('1').convert('L')    # and then halftone ('1') each plane
        m = cmyk[1].convert('1').convert('L')    # ...and back to ('L') mode
        y = cmyk[2].convert('1').convert('L')
        k = cmyk[3].convert('1').convert('L')
    
        new_cmyk = Image.merge('CMYK',[c,m,y,k]) # put together all 4 planes
        new_cmyk.save('tree-cmyk.jpg')           # and save to file
    

    내재 된 GCR PIL 적용은보다 일반적인 것으로도 확장 될 수 있지만 단순한 솔루션을 설명하려고 노력했습니다. 여기에는 해상도와 샘플링도 무시됩니다.

  3. from https://stackoverflow.com/questions/10572274/halftone-images-in-python by cc-by-sa and MIT license