CoolFace
Apppublic

aiqtech/PoseMaker2

sourceHugging Faceapache-2.0updated 3y agoView on Hugging Face
0likes
main.py172 linesDownload Raw Back to root
1import gradio as gr2import json as js3import util4from fastapi.staticfiles import StaticFiles5from fileservice import app6from pose import infer, draw7 8 9def image_changed(image):10  if image == None:11    return "estimation", {}12 13  if 'openpose' in image.info:14    print("pose found")15    jsonText = image.info['openpose']16    jsonObj = js.loads(jsonText)17    subset = jsonObj['subset']18    return f"""{image.width}px x {image.height}px, {len(subset)} indivisual(s)""", jsonText19  else:20    print("pose not found")21    pose_result, returned_outputs = infer(util.pil2cv(image))22 23    candidate = []24    subset = []25    for d in pose_result:26        n = len(candidate)27        if d['bbox'][4] < 0.9: 28            continue29        keypoints = d['keypoints'][:, :2].tolist()30        midpoint = [(keypoints[5][0] + keypoints[6][0]) / 2, (keypoints[5][1] + keypoints[6][1]) / 2]31        keypoints.append(midpoint)32        candidate.extend(util.convert_keypoints(keypoints))33        m = len(candidate)34        subset.append([j for j in range(n, m)])35 36    jsonText = "{ \"candidate\": " + util.candidate_to_json_string(candidate) + ", \"subset\": " + util.subset_to_json_string(subset) + " }"37    return f"""{image.width}px x {image.height}px, {len(subset)} indivisual(s)""", jsonText38 39html_text = f"""40    <canvas id="canvas" width="512" height="512"></canvas><img id="canvas-background" style="display:none;"/>41"""42 43with gr.Blocks(css="""button { min-width: 80px; }""") as demo:44  with gr.Row():45    with gr.Column(scale=1):46      width = gr.Slider(label="Width", minimum=512, maximum=1024, step=64, value=512, interactive=True)47      height = gr.Slider(label="Height", minimum=512, maximum=1024, step=64, value=512, interactive=True)48      with gr.Accordion(label="Pose estimation", open=False):49        source = gr.Image(type="pil")50        estimationResult = gr.Markdown("""estimation""")51        with gr.Row():52          with gr.Column(min_width=80):53            applySizeBtn = gr.Button(value="Apply size")54          with gr.Column(min_width=80):55            replaceBtn = gr.Button(value="Replace")56          with gr.Column(min_width=80):57            importBtn = gr.Button(value="Import")58          with gr.Column(min_width=80):59            bgBtn = gr.Button(value="Background")60          with gr.Column(min_width=80):61            removeBgBtn = gr.Button(value="RemoveBG")62      with gr.Accordion(label="Json", open=False):63        with gr.Row():64          with gr.Column(min_width=80):65            replaceWithJsonBtn = gr.Button(value="Replace")66          with gr.Column(min_width=80):67            importJsonBtn = gr.Button(value="Import")68        gr.Markdown("""69| inout            | how to                                                                               |70| -----------------| ----------------------------------------------------------------------------------------- |71| Import | Paste json to "Json source" and click "Read", edit the width/height, then click "Replace" or "Import". |72| Export | click "Save" and "Copy to clipboard" of "Json" section.                                             |73""")74        json = gr.JSON(label="Json")75        jsonSource = gr.Textbox(label="Json source", lines=10)76      with gr.Accordion(label="Notes", open=False):77        gr.Markdown("""78#### How to bring pose to ControlNet791. Press **Save** button802. **Drag** the file placed at the bottom left corder of browser813. **Drop** the file into ControlNet82 83#### Reuse pose image84Pose image generated by this tool has pose data in the image itself. You can reuse pose information by loading it as the image source instead of a regular image.85 86#### Points to note for pseudo-3D rotation87When performing pseudo-3D rotation on the X and Y axes, the projection is converted to 2D and Z-axis information is lost when the mouse button is released. This means that if you finish dragging while the shape is collapsed, you may not be able to restore it to its original state. In such a case, please use the "undo" function.88 89#### Pose estimation90In this project, MMPose is used for pose estimation.91""")92    with gr.Column(scale=2):93      html = gr.HTML(html_text)94      with gr.Row():95        with gr.Column(scale=1, min_width=60):96          saveBtn = gr.Button(value="Save")97        with gr.Column(scale=7):98          gr.Markdown("""99- "ctrl + drag" to **scale**100- "alt + drag" to **move**101- "shift + drag" to **rotate** (move right first, release shift, then up or down)102- "space + drag" to **range-move**103- "[", "]" or "Alt + wheel" or "Space + wheel" to shrink or expand **range**104- "ctrl + Z", "shift + ctrl + Z" to **undo**, **redo**105- "ctrl + E" **add** new person106- "D + click" to **delete** person107- "Q + click" to **cut off** limb108- "X + drag" to **x-axis** pseudo-3D rotation109- "C + drag" to **y-axis** pseudo-3D rotation110- "R + click" to **repair**111- "H + click" to **hide** node112 113When using Q, X, C, R, pressing and dont release until the operation is complete.114 115[Contact us for feature requests or bug reports (anonymous)](https://t.co/UC3jJOJJtS)116""")117 118  width.change(fn=None, inputs=[width], _js="(w) => { resizeCanvas(w,null); }")119  height.change(fn=None, inputs=[height], _js="(h) => { resizeCanvas(null,h); }")120 121  source.change(122    fn = image_changed,123    inputs = [source],124    outputs = [estimationResult, json])125  applySizeBtn.click(126    fn = lambda x: (x.width, x.height),127    inputs = [source], 128    outputs = [width, height])129  replaceBtn.click(130    fn = None,131    inputs = [json],132    outputs = [],133    _js="(json) => { initializeEditor(); importPose(json); return []; }")134  importBtn.click(135    fn = None,136    inputs = [json],137    outputs = [],138    _js="(json) => { importPose(json); return []; }")139  bgBtn.click(140    fn = None,141    inputs = [source],142    outputs = [],143    _js="(image) => { importBackground(image); return []; }")144  removeBgBtn.click(145    fn = None,146    inputs = [],147    outputs = [],148    _js="() => { importBackground(null); return []; }")149 150  saveBtn.click(151    fn = None,152    inputs = [], outputs = [json],153    _js="() => { return savePose(); }")154  jsonSource.change(155    fn = lambda x: x,156    inputs = [jsonSource], outputs = [json])157  replaceWithJsonBtn.click(158    fn = None,159    inputs = [json],160    outputs = [],161    _js="(json) => { initializeEditor(); importPose(json); return []; }")162  importJsonBtn.click(163    fn = None,164    inputs = [json],165    outputs = [],166    _js="(json) => { importPose(json); return []; }")167  demo.load(fn=None, inputs=[], outputs=[], _js="() => { initializeEditor(); importPose(); return []; }")168 169print("mount")170app.mount("/js", StaticFiles(directory="js"), name="js")171gr.mount_gradio_app(app, demo, path="/")172