<commit_before>// softgel

// When you want to create softgel capsule like shapes, this script may
// help you.  

// USAGE : Draw circles and select them, then run this script.  Adjust
// options in the dialog.  then click OK.
// (This script doesn't check whether each path is really a circle.)

// Note : Combining the shapes using Pathfinder may results several
// overlapping anchor points on the path.  if it occurs, it may help to
// solve it to use my another script "Merge Overlapped Anchors.js
// (http://park12.wakwak.com/~shp/lc/et/en_aics_script.html)
// This script merges overlapping anchors on the path.

// test env: Adobe Illustrator CC (Win/Mac), CS3 (Win)

// Copyright(c) 2013 <NAME>
// https://github.com/shspage
// This script is distributed under the MIT License.
// See the LICENSE file for details.

// Thu, 19 Dec 2013 21:47:06 +0900

main();
function main(){
    var conf = {
        center_angle : 90,
        extra_anchor : "auto",
        errmsg : ""
      }
    
    if (documents.length<1) return;
    var s = activeDocument.selection;
    if (!(s instanceof Array) || s.length<1) return;
    
    var sp = [];
    extractPaths(s, 1, sp);
    if(sp.length < 2) return;
    activateEditableLayer(sp[0]);

    var preview_paths = [];

    var clearPreviewPaths = function(){
        if(preview_paths.length) undo();
        preview_paths = [];
    }
    
    var drawPreview = function(){
        // draws for each paths
        var shape, j;
        for(var i = sp.length - 1; i >= 1; i--){
            for(j = i - 1; j >= 0; j--){
                shape = softgel(sp[i], sp[j], conf);
                if(shape != null) preview_paths.push( shape );
            }
        }
    }
    
    // show a dialog
    var win = new Window("dialog", "Softgel");
    win.orientation = "column";
    win.alignChildren = "fill";

    win.anglePanel = win.add("panel", [15, 15, 240, 61], "center angle");
    win.anglePanel.orientation = "row";
    win.anglePanel.angleSlider = win.anglePanel.add("slider", [15, 10, 165, 27], 90, 1, 180);
    win.anglePanel.valueText = win.anglePanel.add("statictext", [175, 12, 210, 25], 90);
    
    win.radioPanel = win.add("panel", [15, 76, 215, 122], "extra anchor");
    win.radioPanel.orientation = "row";
    win.radioPanel.autoRb = win.radioPanel.add("radiobutton", undefined, "auto");
    win.radioPanel.alwaysRb = win.radioPanel.add("radiobutton", undefined, "always");
    win.radioPanel.neverRb = win.radioPanel.add("radiobutton", undefined, "never");
    win.radioPanel.autoRb.value = true;

    win.chkGroup = win.add("group");
    win.chkGroup.previewChk = win.chkGroup.add("checkbox", undefined, "preview");
    
    win.btnGroup = win.add("group");
    win.btnGroup.okBtn = win.btnGroup.add("button", undefined, "OK");
    win.btnGroup.cancelBtn = win.btnGroup.add("button", undefined, "Cancel");

    var getValues = function(){
        conf.center_angle = win.anglePanel.valueText.text;
        
        if(win.radioPanel.alwaysRb.value){
            conf.extra_anchor = "always";
        } else if(win.radioPanel.neverRb.value){
            conf.extra_anchor = "never";
        } else {
            conf.extra_anchor = "auto";
        }
    }
    
    win.anglePanel.angleSlider.onChanging = function(){
        win.anglePanel.valueText.text = Math.round(this.value);
    }
    
    win.anglePanel.angleSlider.onChange = function(){
        win.anglePanel.valueText.text = Math.round(this.value);
        if(win.chkGroup.previewChk.value){
            getValues();
            clearPreviewPaths();
            drawPreview();
            redraw();
        }
    }
    
    win.btnGroup.okBtn.onClick = function(){
        getValues();
        clearPreviewPaths();
        drawPreview();
        win.close();
    }
    
    win.btnGroup.cancelBtn.onClick = function(){
        clearPreviewPaths();
        win.close();
    }
    win.show();

    activeDocument.selection = sp.concat( preview_paths );
    if( conf.errmsg != "") alert( conf.errmsg );
}

// ---------------------------------------------
function softgel(s0, s1, conf){
    var mpi = Math.PI;
    var hpi = mpi/2;
    
    var arr = getGBCenterWidth(s0);
    var o1 = arr[0];
    var r1 = arr[1] / 2;
    
    arr = getGBCenterWidth(s1);
    var o2 = arr[0];
    var r2 = arr[1] / 2;
    
    if(r1 == 0 || r2 == 0) return;
    
    var d = dist(o1, o2);
    if(d <= Math.abs(r1 - r2)) return;

    // if center_angle is 180, simply draw a circle.
    if(conf.center_angle == 180){
        return (function(){
            var d1 = (d + r2 - r1) / d;
            var d2 = (d + r1 - r2) / d;
            var center = [(o1[0] * d2 + o2[0] * d1) / 2,
                          (o1[1] * d2 + o2[1] * d1) / 2];
            var radius = (d + r1 + r2) / 2;
            var circle = activeDocument.activeLayer.pathItems.ellipse(
                center[1] + radius,
                center[0] - radius,
                radius * 2, radius * 2
                );
            var cp = circle.pathPoints;
            
            var pitem = s0.duplicate();
            var p = pitem.pathPoints;
            
            var i;
            if(p.length > 4) for(i = p.length-1; i > 3; i--) p[i].remove();
            
            var copyPathPoint = function(p1, p2){
                p2.anchor = p1.anchor;
                p2.rightDirection = p1.rightDirection;
                p2.leftDirection = p1.leftDirection;
                p2.pointType = p1.pointType;
            };
            
            for(i = 0; i < 4; i++){
                copyPathPoint(cp[i], p[i]);
            }
            circle.remove();
            return pitem;
        })();
    }
<commit_msg>fixed softgel.jsx (minor issue when center angle = 180)<commit_after>// softgel

// When you want to create softgel capsule like shapes, this script may
// help you.  

// USAGE : Draw circles and select them, then run this script.  Adjust
// options in the dialog.  then click OK.
// (This script doesn't check whether each path is really a circle.)

// Note : Combining the shapes using Pathfinder may results several
// overlapping anchor points on the path.  if it occurs, it may help to
// solve it to use my another script "Merge Overlapped Anchors.js
// (http://park12.wakwak.com/~shp/lc/et/en_aics_script.html)
// This script merges overlapping anchors on the path.

// test env: Adobe Illustrator CC (Win/Mac), CS3 (Win)

// Copyright(c) 2013 <NAME>
// https://github.com/shspage
// This script is distributed under the MIT License.
// See the LICENSE file for details.

// Thu, 19 Dec 2013 21:47:06 +0900

main();
function main(){
    var conf = {
        center_angle : 90,
        extra_anchor : "auto",
        errmsg : ""
      }
    
    if (documents.length<1) return;
    var s = activeDocument.selection;
    if (!(s instanceof Array) || s.length<1) return;
    
    var sp = [];
    extractPaths(s, 1, sp);
    if(sp.length < 2) return;
    activateEditableLayer(sp[0]);

    var preview_paths = [];

    var clearPreviewPaths = function(){
        if(preview_paths.length) undo();
        preview_paths = [];
    }
    
    var drawPreview = function(){
        // draws for each paths
        var shape, j;
        for(var i = sp.length - 1; i >= 1; i--){
            for(j = i - 1; j >= 0; j--){
                shape = softgel(sp[i], sp[j], conf);
                if(shape != null) preview_paths.push( shape );
            }
        }
    }
    
    // show a dialog
    var win = new Window("dialog", "Softgel");
    win.orientation = "column";
    win.alignChildren = "fill";

    win.anglePanel = win.add("panel", [15, 15, 240, 61], "center angle");
    win.anglePanel.orientation = "row";
    win.anglePanel.angleSlider = win.anglePanel.add("slider", [15, 10, 165, 27], 90, 1, 180);
    win.anglePanel.valueText = win.anglePanel.add("statictext", [175, 12, 210, 25], 90);
    
    win.radioPanel = win.add("panel", [15, 76, 215, 122], "extra anchor");
    win.radioPanel.orientation = "row";
    win.radioPanel.autoRb = win.radioPanel.add("radiobutton", undefined, "auto");
    win.radioPanel.alwaysRb = win.radioPanel.add("radiobutton", undefined, "always");
    win.radioPanel.neverRb = win.radioPanel.add("radiobutton", undefined, "never");
    win.radioPanel.autoRb.value = true;

    win.chkGroup = win.add("group");
    win.chkGroup.previewChk = win.chkGroup.add("checkbox", undefined, "preview");
    
    win.btnGroup = win.add("group");
    win.btnGroup.okBtn = win.btnGroup.add("button", undefined, "OK");
    win.btnGroup.cancelBtn = win.btnGroup.add("button", undefined, "Cancel");

    var getValues = function(){
        conf.center_angle = win.anglePanel.valueText.text;
        
        if(win.radioPanel.alwaysRb.value){
            conf.extra_anchor = "always";
        } else if(win.radioPanel.neverRb.value){
            conf.extra_anchor = "never";
        } else {
            conf.extra_anchor = "auto";
        }
    }
    
    win.anglePanel.angleSlider.onChanging = function(){
        win.anglePanel.valueText.text = Math.round(this.value);
    }
    
    win.anglePanel.angleSlider.onChange = function(){
        win.anglePanel.valueText.text = Math.round(this.value);
        if(win.chkGroup.previewChk.value){
            getValues();
            clearPreviewPaths();
            drawPreview();
            redraw();
        }
    }
    
    win.btnGroup.okBtn.onClick = function(){
        getValues();
        clearPreviewPaths();
        drawPreview();
        win.close();
    }
    
    win.btnGroup.cancelBtn.onClick = function(){
        clearPreviewPaths();
        win.close();
    }
    win.show();

    activeDocument.selection = sp.concat( preview_paths );
    if( conf.errmsg != "") alert( conf.errmsg );
}

// ---------------------------------------------
function softgel(s0, s1, conf){
    var mpi = Math.PI;
    var hpi = mpi/2;
    
    var arr = getGBCenterWidth(s0);
    var o1 = arr[0];
    var r1 = arr[1] / 2;
    
    arr = getGBCenterWidth(s1);
    var o2 = arr[0];
    var r2 = arr[1] / 2;
    
    if(r1 == 0 || r2 == 0) return;
    
    var d = dist(o1, o2);
    if(d <= Math.abs(r1 - r2)) return;

    // if center_angle is 180, simply draw a circle.
    if(conf.center_angle == 180){
        return (function(){
            var d1 = (d + r2 - r1) / d;
            var d2 = (d + r1 - r2) / d;
            var center = [(o1[0] * d2 + o2[0] * d1) / 2,
                          (o1[1] * d2 + o2[1] * d1) / 2];
            var radius = (d + r1 + r2) / 2;
            var circle = activeDocument.activeLayer.pathItems.ellipse(
                center[1] + radius,
                center[0] - radius,
                radius * 2, radius * 2
                );
            var cp = circle.pathPoints;
            
            var pitem = s0.duplicate();
            var p = pitem.pathPoints;
            
            while(p.length < 4) p.add();
            while(p.length > 4) p[p.length - 1].remove();
            
            var copyPathPoint = function(p1, p2){
                p2.anchor = p1.anchor;
                p2.rightDirection = p1.rightDirection;
                p2.leftDirection = p1.leftDirection;
                p2.pointType = p1.pointType;
            };
            
            for(var i = 0; i < 4; i++){
                copyPathPoint(cp[i], p[i]);
            }
            circle.remove();
            return pitem;
        })();
    }

{'fraction_non_alphanumeric': 0.1481708384386487, 'fraction_numerical': 0.026868545422720113, 'mean_word_length': 1.900253807106599, 'pattern_counts': {'":': 0, '<': 16, '<?xml version=': 0, '>': 12, 'https://': 2, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5671149', 'n_tokens_mistral': 3846, 'n_tokens_neox': 3600, 'n_words': 901}