복붙노트

[PYTHON] matplotlib의 텍스트 주위 상자

PYTHON

matplotlib의 텍스트 주위 상자

matplotlib에서 텍스트 주위에 상자를 만드는 방법은 무엇입니까? 세 가지 다른 줄과 세 가지 색상으로 된 텍스트가 있습니다.

 ax.text(2,1, 'alpha', color='red')
 ax.text(2,2, 'beta', color='cyan')
 ax.text(2,3, 'epsilon', color='black')

튜토리얼 http://matplotlib.org/users/recipes.html (마지막 예)을 보았지만 문제를 해결할 수 없습니다. 미리 감사드립니다.

해결법

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

    1.멘션에 링크 한 예제처럼 bbox kwarg를 사용하여 상자를 추가 할 수 있습니다.

    멘션에 링크 한 예제처럼 bbox kwarg를 사용하여 상자를 추가 할 수 있습니다.

    상자의 색상 등을 설정하는 방법에 대해 혼란스러워한다고 가정합니다. 빠른 예를 들면 다음과 같습니다.

    import matplotlib.pyplot as plt
    fig, ax = plt.subplots()
    
    ax.text(0.5, 0.8, 'Test', color='red', 
            bbox=dict(facecolor='none', edgecolor='red'))
    
    ax.text(0.5, 0.6, 'Test', color='blue', 
            bbox=dict(facecolor='none', edgecolor='blue', pad=10.0))
    
    ax.text(0.5, 0.4, 'Test', color='green', 
            bbox=dict(facecolor='none', edgecolor='green', boxstyle='round'))
    
    ax.text(0.5, 0.2, 'Test', color='black', 
            bbox=dict(facecolor='none', edgecolor='black', boxstyle='round,pad=1'))
    
    plt.show()
    

    마지막 두 가지는 "멋진"bbox 패치이므로 패딩 등은 다른 방식으로 설정됩니다. (이것은 패딩과 같은 단순한 것들에 대해 다소 성가시다.하지만 구현이 더 간단하게 보이지 않게한다.)

    또한, 플롯에서 사물에 라벨을 붙이면, 아마 주석이 더 나은 선택이라는 것을 알게 될 것입니다. 무엇보다도 특정 데이터 위치에서 벗어난 위치에 텍스트를 배치 할 수 있습니다.

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

    2.VPacker와 AnnotationBbox를 사용하여 다양한 글꼴 속성의 여러 텍스트를 함께 사용하기위한 어딘가의 온라인 설명서가 있습니다 (빨리 찾을 수있는 가장 좋은 방법은 http://matplotlib.org/users/annotations_guide.html입니다).

    VPacker와 AnnotationBbox를 사용하여 다양한 글꼴 속성의 여러 텍스트를 함께 사용하기위한 어딘가의 온라인 설명서가 있습니다 (빨리 찾을 수있는 가장 좋은 방법은 http://matplotlib.org/users/annotations_guide.html입니다).

    from matplotlib.offsetbox import TextArea, VPacker, AnnotationBbox
    from pylab import *
    fig = figure(1)
    ax = gca()
    texts = ['alpha','beta','epsilon']
    colors = ['red','cyan','black']
    Texts = []
    for t,c in zip(texts,colors):
        Texts.append(TextArea(t,textprops=dict(color=c)))
    texts_vbox = VPacker(children=Texts,pad=0,sep=0)
    ann = AnnotationBbox(texts_vbox,(.02,.5),xycoords=ax.transAxes,
                                box_alignment=(0,.5),bboxprops = 
                                dict(facecolor='wheat',boxstyle='round',color='black'))
    ann.set_figure(fig)
    fig.artists.append(ann)
    

    나는 왜 마지막 두 라인 모두가 필요한지 잘 모르겠습니다. 나는 둘째로 충분할 것이라고 생각한다.

  3. ==============================

    3.해결책은 텍스트 객체에서 boundingbox를 탐색하고 직접 상자를 생성하는 것입니다. 매우 편리하지 않습니다. 아마 나의 예가 향상 될 수 있으며, 변환은 항상 나를 혼란스럽게합니다.

    해결책은 텍스트 객체에서 boundingbox를 탐색하고 직접 상자를 생성하는 것입니다. 매우 편리하지 않습니다. 아마 나의 예가 향상 될 수 있으며, 변환은 항상 나를 혼란스럽게합니다.

    import matplotlib.patches as patches
    import matplotlib.pyplot as plt
    
    fig, axs = plt.subplots(1,1)
    
    t1 = axs.text(0.4,0.6, 'Hello world line 1', ha='center', color='red', weight='bold', transform=axs.transAxes)
    t2 = axs.text(0.5,0.5, 'Hello world line 2', ha='center', color='green', weight='bold', transform=axs.transAxes)
    t3 = axs.text(0.6,0.4, 'Hello world line 3', ha='center', color='blue', weight='bold', transform=axs.transAxes)
    
    fig.canvas.draw()
    
    textobjs = [t1,t2,t3]
    
    xmin = min([t.get_window_extent().xmin for t in textobjs])
    xmax = max([t.get_window_extent().xmax for t in textobjs])
    ymin = min([t.get_window_extent().ymin for t in textobjs])
    ymax = max([t.get_window_extent().ymax for t in textobjs])
    
    xmin, ymin = fig.transFigure.inverted().transform((xmin, ymin))
    xmax, ymax = fig.transFigure.inverted().transform((xmax, ymax))
    
    rect = patches.Rectangle((xmin,ymin),xmax-xmin,ymax-ymin, facecolor='grey', alpha=0.2, transform=fig.transFigure)
    
    axs.add_patch(rect)
    

    작은 버퍼 등을 추가 할 수도 있지만, 아이디어는 그대로 유지됩니다.

  4. from https://stackoverflow.com/questions/17086847/box-around-text-in-matplotlib by cc-by-sa and MIT license