【AdobeXD】プラグイン開発2 Content


# 目標
基本的なAPIを学ぶ


## ログ
`console.log("HelloWorld!");`

![スクリーンショット 2018-10-17 22.48.23.png](https://qiita-image-store.s3.amazonaws.com/0/113504/706f92bd-6984-1c6e-8bb8-856275a899a7.png "スクリーンショット 2018-10-17 22.48.23.png")

コンソールにログを表示できる

![スクリーンショット 2018-10-17 22.48.35.png](https://qiita-image-store.s3.amazonaws.com/0/113504/31a65eca-bf80-ea7e-7962-7b13d220b173.png "スクリーンショット 2018-10-17 22.48.35.png")

# 図形の作成

## 長方形を作る

![スクリーンショット 2018-10-18 12.25.07.png](https://qiita-image-store.s3.amazonaws.com/0/113504/741f5b0a-d90a-9c66-f013-00f71b022759.png "スクリーンショット 2018-10-18 12.25.07.png")

```create_rectangle.js
// 1. scenegraphの機能を使う
const {Rectangle, Color} = require("scenegraph");

function myPluginCommand(selection) {
    console.log("create rectangle");
    // 2. 長方形を生成
    const rect = new Rectangle();
    // 3. 各プロパティーを設定
    rect.width = 100;
    rect.height = 25;
    rect.fill = new Color("red");
    // 4. XDノードツリーにテキストオブジェクトを追加
    selection.insertionParent.addChild(rect);
}
```

### ポイント
Rectangle 長方形
Color 色
selection.insertionParent.addChild(rect); ノードとして追加


## 線を引く



![スクリーンショット 2018-10-19 23.55.35.png](https://qiita-image-store.s3.amazonaws.com/0/113504/b2a019fc-1850-731c-0f46-427111c00abf.png "スクリーンショット 2018-10-19 23.55.35.png")

```LineTutorial.js
const {Line, Color} = require("scenegraph");
const commands = require("commands");

// 線の始点と終点の情報
const lineData = [
    { startX: 100, startY: 110, endX: 210, endY: 233 },
    { startX: 210, startY: 233, endX: 320, endY: 156 },
    { startX: 320, startY: 156, endX: 400, endY: 300 },
    { startX: 400, startY: 300, endX: 500, endY: 120 }
]

// ランダムな色を生成する関数
const randomColor = () => {
    const hexValues = ['00', '33', '66', '99', 'CC', 'FF'];
    const color = "#" + Array.from({ length: 3 }, _ => hexValues[Math.floor(Math.random() * hexValues.length)]).join("");
    return color;
}

// 線を引く
const myPluginCommand = (selection) => {
    let lines = lineData.map(data => {
        const line = new Line(); // Lineのインスタンスを生成
        
        // Lineの始点と終点を設定
        line.setStartEnd(
            data.startX,
            data.startY,
            data.endX,
            data.endY
        );
        
        // Lineの境界線(実質線の情報)を設定
        line.strokeEnabled = true;
        line.stroke = new Color(randomColor());
        line.strokeWidth = 3;

        selection.insertionParent.addChild(line);
        return line;
    });
    
    // linesを選択する
    selection.items = lines;
    
    // 選択したノード(lines)をグループ化
    commands.group();
}
```

線を引くチュートリアル．
ES6について学んだので書き方はチュートリアルから変えました．

### ポイント
Line 線
stroke 境界線

```グループ化.js
selection.items = targets;
commands.group();
```

## 円形グラフ

![スクリーンショット 2018-10-28 13.13.27.png](https://qiita-image-store.s3.amazonaws.com/0/113504/5485a8fc-ebeb-a246-1fd4-c0e47c0d9677.png "スクリーンショット 2018-10-28 13.13.27.png")


```PieChartTutorial.js
const { Path, Color } = require("scenegraph");
const commands = require("commands");

// 円周上の点の座標を"px,py"を取得
const pointOnCircle = (radius, angle) => {
    const radians = angle * 2. * Math.PI / 360.;
    const xcoord = radius * Math.cos(radians);
    const ycoord = radius * Math.sin(radians);
    return xcoord + "," + ycoord;
}

// 扇型の図形を作成
const createWedge = (selection, radius, startAngle, endAngle, color) => {
    const startPt = pointOnCircle(radius, startAngle);
    const endPt = pointOnCircle(radius, endAngle);
    const pathData = `M0,0 L${startPt} A${radius},${radius},0,0,1,${endPt} L0,0`; // 扇型のパスのデータ
    const wedge = new Path();
    wedge.pathData = pathData;
    wedge.fill = new Color(color);
    wedge.translation = {x: radius, y: radius};
    selection.insertionParent.addChild(wedge);
    return wedge;
}

// パイチャートを作成
const createPieChart = (selection) => {
    const wedges = [
        createWedge(selection, 100, 0, 90, "red"),
        createWedge(selection, 100, 90, 135, "blue"),
        createWedge(selection, 100, 135, 225, "yellow"),
        createWedge(selection, 100, 225, 360, "purple")
    ];
    selection.items = wedges;
    commands.group();
}

const myPluginCommand = (selection) => {
    createPieChart(selection);
}
```

### ポイント
Pathを使うのには専用の書き方を学ぶ必要がある．
今回はスキップします

# 文字の生成
![スクリーンショット 2018-10-28 13.51.07.png](https://qiita-image-store.s3.amazonaws.com/0/113504/9af22c18-c479-1f73-e179-33ee02620912.png "スクリーンショット 2018-10-28 13.51.07.png")

```TextTutorial.js
// Style Text Tutorial
const { Text, Color } = require("scenegraph");


const createStyledText = (selection) => {
    
    const node = new Text();               
    node.text = "This is some red text"; 
    node.styleRanges = [{ 
        length: node.text.length,
        fill: new Color("#FF0000"),
        fontSize: 24
    }];

    selection.insertionParent.addChild(node);
    node.moveInParentCoordinates(20, 50);
}


const myPluginCommand = (selection) => {
    createStyledText(selection);
}
```

> 2018年10月　公式チュートリアルは`node.styleRanges`を`node.styleRange`と間違えているため動かないことに注意

![スクリーンショット 2018-10-28 14.04.12.png](https://qiita-image-store.s3.amazonaws.com/0/113504/834380d3-8d63-e1f5-dc53-69ed7e07c7e9.png "スクリーンショット 2018-10-28 14.04.12.png")

```StyleTextTutorial.js
// Style Text Tutorial
const { Text, Color } = require("scenegraph");


const createStyledText = (selection) => {
    
    const node = new Text();
    
    const textDataList = [
        {text: "This ", color: "red"},
        {text: "is ", color: "orange"},
        {text: "some ", color: "yellow"},
        {text: "Colorful ", color: "green"},
        {text: "Text ", color: "blue"},
    ]
    node.text = textDataList.map(item => item.text).join(""); // テキストを連結

    node.styleRanges = textDataList.map(item => ({
        length: item.text.length,
        fill: new Color(item.color),
        fontSize: 24
    }));

    selection.insertionParent.addChild(node);
    node.moveInParentCoordinates(20, 50);
}


const myPluginCommand = (selection) => {
    createStyledText(selection);
}
```

### ポイント
styleRanges テキストのスタイルの配列
テキストの要素を分解することで各要素のStyleを設定できる

## 全ての長方形の色を変える

![スクリーンショット 2018-10-28 14.52.11.png](https://qiita-image-store.s3.amazonaws.com/0/113504/c5f82514-e42d-f4ab-435a-4619713dccfe.png "スクリーンショット 2018-10-28 14.52.11.png")


フィルター

```filter.js
// 全てのRectangleを赤くする
const filterAndColor = (selection, documentRoot) => {
    // SceneNode.childrenでSceneNodeListを参照 foreachで子SceneNodeを取得
    documentRoot.children.forEach(node => {
        if(node instanceof Artboard){ // documentRoot > artBoard > 各グループが基本の構成なのでまずartBoardを取得
            let artboard = node;
            let rectangles = artboard.children.filter(artboardChild => {
                return artboardChild instanceof Rectangle;
            })
            rectangles.forEach(rectangle => {
                rectangle.fill = new Color("red");
            })
        }
    })
}

...

module.exports = {
    commands: {
        createElements, // こっちは生成用
        filterAndColor
    }
};
```

https://adobexdplatform.com/plugin-docs/reference/scenegraph.html#Point

### ポイント
documentRoot ルートを引数としてわたせる
SceneNodeList SceneNode.children で子を取得できる，配列ではないことに注意
x instanceof y xがyのinstanceならtrueを返す