mirror of
				https://github.com/zadam/trilium.git
				synced 2025-11-03 20:06:08 +01:00 
			
		
		
		
	bulk action dialog converted to widget
This commit is contained in:
		
							
								
								
									
										97
									
								
								package-lock.json
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										97
									
								
								package-lock.json
									
									
									
										generated
									
									
									
								
							@@ -1,12 +1,12 @@
 | 
			
		||||
{
 | 
			
		||||
  "name": "trilium",
 | 
			
		||||
  "version": "0.52.0-beta",
 | 
			
		||||
  "version": "0.52.2",
 | 
			
		||||
  "lockfileVersion": 2,
 | 
			
		||||
  "requires": true,
 | 
			
		||||
  "packages": {
 | 
			
		||||
    "": {
 | 
			
		||||
      "name": "trilium",
 | 
			
		||||
      "version": "0.52.0-beta",
 | 
			
		||||
      "version": "0.52.2",
 | 
			
		||||
      "hasInstallScript": true,
 | 
			
		||||
      "license": "AGPL-3.0-only",
 | 
			
		||||
      "dependencies": {
 | 
			
		||||
@@ -21,7 +21,7 @@
 | 
			
		||||
        "commonmark": "0.30.0",
 | 
			
		||||
        "cookie-parser": "1.4.6",
 | 
			
		||||
        "csurf": "1.11.0",
 | 
			
		||||
        "dayjs": "1.11.2",
 | 
			
		||||
        "dayjs": "1.11.3",
 | 
			
		||||
        "ejs": "3.1.8",
 | 
			
		||||
        "electron-debug": "3.2.0",
 | 
			
		||||
        "electron-dl": "3.3.1",
 | 
			
		||||
@@ -65,7 +65,7 @@
 | 
			
		||||
        "tmp": "0.2.1",
 | 
			
		||||
        "turndown": "7.1.1",
 | 
			
		||||
        "unescape": "1.0.1",
 | 
			
		||||
        "ws": "8.7.0",
 | 
			
		||||
        "ws": "8.8.0",
 | 
			
		||||
        "yauzl": "2.10.0"
 | 
			
		||||
      },
 | 
			
		||||
      "bin": {
 | 
			
		||||
@@ -78,9 +78,9 @@
 | 
			
		||||
        "electron-packager": "15.5.1",
 | 
			
		||||
        "electron-rebuild": "3.2.7",
 | 
			
		||||
        "esm": "3.2.25",
 | 
			
		||||
        "jasmine": "4.1.0",
 | 
			
		||||
        "jasmine": "4.2.0",
 | 
			
		||||
        "jsdoc": "3.6.10",
 | 
			
		||||
        "lorem-ipsum": "2.0.4",
 | 
			
		||||
        "lorem-ipsum": "2.0.8",
 | 
			
		||||
        "rcedit": "3.0.1",
 | 
			
		||||
        "webpack": "5.73.0",
 | 
			
		||||
        "webpack-cli": "4.9.2"
 | 
			
		||||
@@ -3093,9 +3093,9 @@
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "node_modules/dayjs": {
 | 
			
		||||
      "version": "1.11.2",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/dayjs/-/dayjs-1.11.2.tgz",
 | 
			
		||||
      "integrity": "sha512-F4LXf1OeU9hrSYRPTTj/6FbO4HTjPKXvEIC1P2kcnFurViINCVk3ZV0xAS3XVx9MkMsXbbqlK6hjseaYbgKEHw=="
 | 
			
		||||
      "version": "1.11.3",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/dayjs/-/dayjs-1.11.3.tgz",
 | 
			
		||||
      "integrity": "sha512-xxwlswWOlGhzgQ4TKzASQkUhqERI3egRNqgV4ScR8wlANA/A9tZ7miXa44vTTKEq5l7vWoL5G57bG3zA+Kow0A=="
 | 
			
		||||
    },
 | 
			
		||||
    "node_modules/debug": {
 | 
			
		||||
      "version": "4.3.4",
 | 
			
		||||
@@ -6337,22 +6337,22 @@
 | 
			
		||||
      "integrity": "sha512-spZRyzKL5l5BZQrr/6m/SqFdBN0q3OCI0f9rjfBzCMBIP4p75P620rR3gTmaksNOhmzgdxcaxdNfMy6anrbM0g=="
 | 
			
		||||
    },
 | 
			
		||||
    "node_modules/jasmine": {
 | 
			
		||||
      "version": "4.1.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/jasmine/-/jasmine-4.1.0.tgz",
 | 
			
		||||
      "integrity": "sha512-4VhjbUgwfNS9CBnUMoSWr9tdNgOoOhNIjAD8YRxTn+PmOf4qTSC0Uqhk66dWGnz2vJxtNIU0uBjiwnsp4Ud9VA==",
 | 
			
		||||
      "version": "4.2.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/jasmine/-/jasmine-4.2.0.tgz",
 | 
			
		||||
      "integrity": "sha512-6SQRXHs5O++mp52PkoJoi9zuLYqp1IaqepRNmAQn5rUBo9VUnckpkkXQQD5PAuCCVVB1ULDImvWYCPV/ZVnaGQ==",
 | 
			
		||||
      "dev": true,
 | 
			
		||||
      "dependencies": {
 | 
			
		||||
        "glob": "^7.1.6",
 | 
			
		||||
        "jasmine-core": "^4.1.0"
 | 
			
		||||
        "jasmine-core": "^4.2.0"
 | 
			
		||||
      },
 | 
			
		||||
      "bin": {
 | 
			
		||||
        "jasmine": "bin/jasmine.js"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "node_modules/jasmine-core": {
 | 
			
		||||
      "version": "4.1.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/jasmine-core/-/jasmine-core-4.1.0.tgz",
 | 
			
		||||
      "integrity": "sha512-8E8BiffCL8sBwK1zU9cbavLe8xpJAgOduSJ6N8PJVv8VosQ/nxVTuXj2kUeHxTlZBVvh24G19ga7xdiaxlceKg==",
 | 
			
		||||
      "version": "4.2.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/jasmine-core/-/jasmine-core-4.2.0.tgz",
 | 
			
		||||
      "integrity": "sha512-OcFpBrIhnbmb9wfI8cqPSJ50pv3Wg4/NSgoZIqHzIwO/2a9qivJWzv8hUvaREIMYYJBas6AvfXATFdVuzzCqVw==",
 | 
			
		||||
      "dev": true
 | 
			
		||||
    },
 | 
			
		||||
    "node_modules/jest-worker": {
 | 
			
		||||
@@ -6855,12 +6855,12 @@
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "node_modules/lorem-ipsum": {
 | 
			
		||||
      "version": "2.0.4",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/lorem-ipsum/-/lorem-ipsum-2.0.4.tgz",
 | 
			
		||||
      "integrity": "sha512-TD+ERYfxjYiUfOyaKU6OH4euumNVeKoo3BxIhokb7bGmoCULsME48onF9NVxYK3CU1z9L5ALnkDkW8lIkHvMNQ==",
 | 
			
		||||
      "version": "2.0.8",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/lorem-ipsum/-/lorem-ipsum-2.0.8.tgz",
 | 
			
		||||
      "integrity": "sha512-5RIwHuCb979RASgCJH0VKERn9cQo/+NcAi2BMe9ddj+gp7hujl6BI+qdOG4nVsLDpwWEJwTVYXNKP6BGgbcoGA==",
 | 
			
		||||
      "dev": true,
 | 
			
		||||
      "dependencies": {
 | 
			
		||||
        "commander": "^2.17.1"
 | 
			
		||||
        "commander": "^9.3.0"
 | 
			
		||||
      },
 | 
			
		||||
      "bin": {
 | 
			
		||||
        "lorem-ipsum": "dist/bin/lorem-ipsum.bin.js"
 | 
			
		||||
@@ -6871,10 +6871,13 @@
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "node_modules/lorem-ipsum/node_modules/commander": {
 | 
			
		||||
      "version": "2.20.3",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz",
 | 
			
		||||
      "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==",
 | 
			
		||||
      "dev": true
 | 
			
		||||
      "version": "9.3.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/commander/-/commander-9.3.0.tgz",
 | 
			
		||||
      "integrity": "sha512-hv95iU5uXPbK83mjrJKuZyFM/LBAoCV/XhVGkS5Je6tl7sxr6A0ITMw5WoRV46/UaJ46Nllm3Xt7IaJhXTIkzw==",
 | 
			
		||||
      "dev": true,
 | 
			
		||||
      "engines": {
 | 
			
		||||
        "node": "^12.20.0 || >=14"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "node_modules/lowercase-keys": {
 | 
			
		||||
      "version": "1.0.1",
 | 
			
		||||
@@ -10538,9 +10541,9 @@
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "node_modules/ws": {
 | 
			
		||||
      "version": "8.7.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/ws/-/ws-8.7.0.tgz",
 | 
			
		||||
      "integrity": "sha512-c2gsP0PRwcLFzUiA8Mkr37/MI7ilIlHQxaEAtd0uNMbVMoy8puJyafRlm0bV9MbGSabUPeLrRRaqIBcFcA2Pqg==",
 | 
			
		||||
      "version": "8.8.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/ws/-/ws-8.8.0.tgz",
 | 
			
		||||
      "integrity": "sha512-JDAgSYQ1ksuwqfChJusw1LSJ8BizJ2e/vVu5Lxjq3YvNJNlROv1ui4i+c/kUUrPheBvQl4c5UbERhTwKa6QBJQ==",
 | 
			
		||||
      "engines": {
 | 
			
		||||
        "node": ">=10.0.0"
 | 
			
		||||
      },
 | 
			
		||||
@@ -13191,9 +13194,9 @@
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "dayjs": {
 | 
			
		||||
      "version": "1.11.2",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/dayjs/-/dayjs-1.11.2.tgz",
 | 
			
		||||
      "integrity": "sha512-F4LXf1OeU9hrSYRPTTj/6FbO4HTjPKXvEIC1P2kcnFurViINCVk3ZV0xAS3XVx9MkMsXbbqlK6hjseaYbgKEHw=="
 | 
			
		||||
      "version": "1.11.3",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/dayjs/-/dayjs-1.11.3.tgz",
 | 
			
		||||
      "integrity": "sha512-xxwlswWOlGhzgQ4TKzASQkUhqERI3egRNqgV4ScR8wlANA/A9tZ7miXa44vTTKEq5l7vWoL5G57bG3zA+Kow0A=="
 | 
			
		||||
    },
 | 
			
		||||
    "debug": {
 | 
			
		||||
      "version": "4.3.4",
 | 
			
		||||
@@ -15649,19 +15652,19 @@
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "jasmine": {
 | 
			
		||||
      "version": "4.1.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/jasmine/-/jasmine-4.1.0.tgz",
 | 
			
		||||
      "integrity": "sha512-4VhjbUgwfNS9CBnUMoSWr9tdNgOoOhNIjAD8YRxTn+PmOf4qTSC0Uqhk66dWGnz2vJxtNIU0uBjiwnsp4Ud9VA==",
 | 
			
		||||
      "version": "4.2.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/jasmine/-/jasmine-4.2.0.tgz",
 | 
			
		||||
      "integrity": "sha512-6SQRXHs5O++mp52PkoJoi9zuLYqp1IaqepRNmAQn5rUBo9VUnckpkkXQQD5PAuCCVVB1ULDImvWYCPV/ZVnaGQ==",
 | 
			
		||||
      "dev": true,
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "glob": "^7.1.6",
 | 
			
		||||
        "jasmine-core": "^4.1.0"
 | 
			
		||||
        "jasmine-core": "^4.2.0"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "jasmine-core": {
 | 
			
		||||
      "version": "4.1.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/jasmine-core/-/jasmine-core-4.1.0.tgz",
 | 
			
		||||
      "integrity": "sha512-8E8BiffCL8sBwK1zU9cbavLe8xpJAgOduSJ6N8PJVv8VosQ/nxVTuXj2kUeHxTlZBVvh24G19ga7xdiaxlceKg==",
 | 
			
		||||
      "version": "4.2.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/jasmine-core/-/jasmine-core-4.2.0.tgz",
 | 
			
		||||
      "integrity": "sha512-OcFpBrIhnbmb9wfI8cqPSJ50pv3Wg4/NSgoZIqHzIwO/2a9qivJWzv8hUvaREIMYYJBas6AvfXATFdVuzzCqVw==",
 | 
			
		||||
      "dev": true
 | 
			
		||||
    },
 | 
			
		||||
    "jest-worker": {
 | 
			
		||||
@@ -16075,18 +16078,18 @@
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "lorem-ipsum": {
 | 
			
		||||
      "version": "2.0.4",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/lorem-ipsum/-/lorem-ipsum-2.0.4.tgz",
 | 
			
		||||
      "integrity": "sha512-TD+ERYfxjYiUfOyaKU6OH4euumNVeKoo3BxIhokb7bGmoCULsME48onF9NVxYK3CU1z9L5ALnkDkW8lIkHvMNQ==",
 | 
			
		||||
      "version": "2.0.8",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/lorem-ipsum/-/lorem-ipsum-2.0.8.tgz",
 | 
			
		||||
      "integrity": "sha512-5RIwHuCb979RASgCJH0VKERn9cQo/+NcAi2BMe9ddj+gp7hujl6BI+qdOG4nVsLDpwWEJwTVYXNKP6BGgbcoGA==",
 | 
			
		||||
      "dev": true,
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "commander": "^2.17.1"
 | 
			
		||||
        "commander": "^9.3.0"
 | 
			
		||||
      },
 | 
			
		||||
      "dependencies": {
 | 
			
		||||
        "commander": {
 | 
			
		||||
          "version": "2.20.3",
 | 
			
		||||
          "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz",
 | 
			
		||||
          "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==",
 | 
			
		||||
          "version": "9.3.0",
 | 
			
		||||
          "resolved": "https://registry.npmjs.org/commander/-/commander-9.3.0.tgz",
 | 
			
		||||
          "integrity": "sha512-hv95iU5uXPbK83mjrJKuZyFM/LBAoCV/XhVGkS5Je6tl7sxr6A0ITMw5WoRV46/UaJ46Nllm3Xt7IaJhXTIkzw==",
 | 
			
		||||
          "dev": true
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
@@ -18915,9 +18918,9 @@
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "ws": {
 | 
			
		||||
      "version": "8.7.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/ws/-/ws-8.7.0.tgz",
 | 
			
		||||
      "integrity": "sha512-c2gsP0PRwcLFzUiA8Mkr37/MI7ilIlHQxaEAtd0uNMbVMoy8puJyafRlm0bV9MbGSabUPeLrRRaqIBcFcA2Pqg==",
 | 
			
		||||
      "version": "8.8.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/ws/-/ws-8.8.0.tgz",
 | 
			
		||||
      "integrity": "sha512-JDAgSYQ1ksuwqfChJusw1LSJ8BizJ2e/vVu5Lxjq3YvNJNlROv1ui4i+c/kUUrPheBvQl4c5UbERhTwKa6QBJQ==",
 | 
			
		||||
      "requires": {}
 | 
			
		||||
    },
 | 
			
		||||
    "xdg-basedir": {
 | 
			
		||||
 
 | 
			
		||||
@@ -80,7 +80,7 @@
 | 
			
		||||
    "tmp": "0.2.1",
 | 
			
		||||
    "turndown": "7.1.1",
 | 
			
		||||
    "unescape": "1.0.1",
 | 
			
		||||
    "ws": "8.7.0",
 | 
			
		||||
    "ws": "8.8.0",
 | 
			
		||||
    "yauzl": "2.10.0"
 | 
			
		||||
  },
 | 
			
		||||
  "devDependencies": {
 | 
			
		||||
@@ -90,9 +90,9 @@
 | 
			
		||||
    "electron-packager": "15.5.1",
 | 
			
		||||
    "electron-rebuild": "3.2.7",
 | 
			
		||||
    "esm": "3.2.25",
 | 
			
		||||
    "jasmine": "4.1.0",
 | 
			
		||||
    "jasmine": "4.2.0",
 | 
			
		||||
    "jsdoc": "3.6.10",
 | 
			
		||||
    "lorem-ipsum": "2.0.4",
 | 
			
		||||
    "lorem-ipsum": "2.0.8",
 | 
			
		||||
    "rcedit": "3.0.1",
 | 
			
		||||
    "webpack": "5.73.0",
 | 
			
		||||
    "webpack-cli": "4.9.2"
 | 
			
		||||
 
 | 
			
		||||
@@ -50,6 +50,7 @@ import BacklinksWidget from "../widgets/backlinks.js";
 | 
			
		||||
import SharedInfoWidget from "../widgets/shared_info.js";
 | 
			
		||||
import FindWidget from "../widgets/find.js";
 | 
			
		||||
import TocWidget from "../widgets/toc.js";
 | 
			
		||||
import BulkActionsDialog from "../widgets/dialogs/bulk_actions.js";
 | 
			
		||||
 | 
			
		||||
export default class DesktopLayout {
 | 
			
		||||
    constructor(customWidgets) {
 | 
			
		||||
@@ -174,6 +175,7 @@ export default class DesktopLayout {
 | 
			
		||||
                        .child(...this.customWidgets.get('right-pane'))
 | 
			
		||||
                    )
 | 
			
		||||
                )
 | 
			
		||||
            );
 | 
			
		||||
            )
 | 
			
		||||
            .child(new BulkActionsDialog());
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -91,7 +91,7 @@ class TreeContextMenu {
 | 
			
		||||
                enabled: notSearch && noSelectedNotes },
 | 
			
		||||
            { title: "Import into note", command: "importIntoNote", uiIcon: "bx bx-empty",
 | 
			
		||||
                enabled: notSearch && noSelectedNotes },
 | 
			
		||||
            { title: "Bulk assign attributes", command: "bulkAssignAttributes", uiIcon: "bx bx-empty",
 | 
			
		||||
            { title: "Bulk actions", command: "bulkActions", uiIcon: "bx bx-empty",
 | 
			
		||||
                enabled: true }
 | 
			
		||||
        ].filter(row => row !== null);
 | 
			
		||||
    }
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,5 @@
 | 
			
		||||
import server from "../../services/server.js";
 | 
			
		||||
import ws from "../../services/ws.js";
 | 
			
		||||
import Component from "../component.js";
 | 
			
		||||
import utils from "../../services/utils.js";
 | 
			
		||||
 | 
			
		||||
export default class AbstractBulkAction {
 | 
			
		||||
@@ -48,6 +47,6 @@ export default class AbstractBulkAction {
 | 
			
		||||
 | 
			
		||||
        await ws.waitForMaxKnownEntityChangeId();
 | 
			
		||||
 | 
			
		||||
        await this.triggerCommand('refreshSearchDefinition');
 | 
			
		||||
        //await this.triggerCommand('refreshSearchDefinition');
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -5,7 +5,7 @@ const TPL = `
 | 
			
		||||
<tr>
 | 
			
		||||
    <td colspan="2">
 | 
			
		||||
        <div style="display: flex; align-items: center">
 | 
			
		||||
            <div style="margin-right: 10px;">Rename label from:</div> 
 | 
			
		||||
            <div style="margin-right: 10px; flex-shrink: 0;">Rename label from:</div> 
 | 
			
		||||
            
 | 
			
		||||
            <input type="text" 
 | 
			
		||||
                class="form-control old-label-name" 
 | 
			
		||||
@@ -45,7 +45,7 @@ export default class RenameLabelBulkAction extends AbstractBulkAction {
 | 
			
		||||
                oldLabelName: $oldLabelName.val(),
 | 
			
		||||
                newLabelName: $newLabelName.val()
 | 
			
		||||
            });
 | 
			
		||||
        }, 1000)
 | 
			
		||||
        }, 1000);
 | 
			
		||||
 | 
			
		||||
        $oldLabelName.on('input', () => spacedUpdate.scheduleUpdate());
 | 
			
		||||
        $newLabelName.on('input', () => spacedUpdate.scheduleUpdate());
 | 
			
		||||
 
 | 
			
		||||
@@ -5,7 +5,7 @@ const TPL = `
 | 
			
		||||
<tr>
 | 
			
		||||
    <td colspan="2">
 | 
			
		||||
        <div style="display: flex; align-items: center">
 | 
			
		||||
            <div style="margin-right: 10px;">Rename relation from:</div> 
 | 
			
		||||
            <div style="margin-right: 10px; flex-shrink: 0;">Rename relation from:</div> 
 | 
			
		||||
            
 | 
			
		||||
            <input type="text" 
 | 
			
		||||
                class="form-control old-relation-name" 
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										132
									
								
								src/public/app/widgets/dialogs/bulk_actions.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										132
									
								
								src/public/app/widgets/dialogs/bulk_actions.js
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,132 @@
 | 
			
		||||
import BasicWidget from "../basic_widget.js";
 | 
			
		||||
import froca from "../../services/froca.js";
 | 
			
		||||
import bulkActionService from "../../services/bulk_action.js";
 | 
			
		||||
import utils from "../../services/utils.js";
 | 
			
		||||
 | 
			
		||||
const TPL = `
 | 
			
		||||
<div class="bulk-assign-attributes-dialog modal mx-auto" tabindex="-1" role="dialog">
 | 
			
		||||
    <style>
 | 
			
		||||
        .bulk-assign-attributes-dialog .modal-body h4:not(:first-child) {
 | 
			
		||||
            margin-top: 20px;
 | 
			
		||||
        }
 | 
			
		||||
    
 | 
			
		||||
        .bulk-available-action-list button {
 | 
			
		||||
            padding: 2px 7px;
 | 
			
		||||
            margin-right: 10px;
 | 
			
		||||
            margin-bottom: 5px;
 | 
			
		||||
        }
 | 
			
		||||
    
 | 
			
		||||
        .bulk-existing-action-list {
 | 
			
		||||
            width: 100%;
 | 
			
		||||
        }
 | 
			
		||||
    
 | 
			
		||||
        .bulk-existing-action-list td {
 | 
			
		||||
            padding: 7px;
 | 
			
		||||
        }
 | 
			
		||||
    
 | 
			
		||||
        .bulk-existing-action-list .button-column {
 | 
			
		||||
            /* minimal width so that table remains static sized and most space remains for middle column with settings */
 | 
			
		||||
            width: 50px;
 | 
			
		||||
            white-space: nowrap;
 | 
			
		||||
            text-align: right;
 | 
			
		||||
        }
 | 
			
		||||
    </style>
 | 
			
		||||
 | 
			
		||||
    <div class="modal-dialog modal-xl" role="document">
 | 
			
		||||
        <div class="modal-content">
 | 
			
		||||
            <div class="modal-header">
 | 
			
		||||
                <h5 class="modal-title mr-auto">Bulk assign attributes</h5>
 | 
			
		||||
 | 
			
		||||
                <button type="button" class="close" data-dismiss="modal" aria-label="Close" style="margin-left: 0 !important;">
 | 
			
		||||
                    <span aria-hidden="true">×</span>
 | 
			
		||||
                </button>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div class="modal-body">
 | 
			
		||||
                <h4>Affected notes: <span class="affected-note-count">0</span></h4>
 | 
			
		||||
 | 
			
		||||
                <div class="form-check">
 | 
			
		||||
                    <input class="form-check-input" type="checkbox" value="" class="include-descendants">
 | 
			
		||||
                    <label class="form-check-label" for="include-descendants">
 | 
			
		||||
                        Include descendant notes
 | 
			
		||||
                    </label>
 | 
			
		||||
                </div>
 | 
			
		||||
 | 
			
		||||
                <h4>Available actions</h4>
 | 
			
		||||
 | 
			
		||||
                <table class="bulk-available-action-list"></table>
 | 
			
		||||
 | 
			
		||||
                <h4>Chosen actions</h4>
 | 
			
		||||
 | 
			
		||||
                <table class="bulk-existing-action-list"></table>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div class="modal-footer">
 | 
			
		||||
                <button type="submit" class="btn btn-primary">Execute bulk actions</button>
 | 
			
		||||
            </div>
 | 
			
		||||
        </div>
 | 
			
		||||
    </div>
 | 
			
		||||
</div>`;
 | 
			
		||||
 | 
			
		||||
export default class BulkActionsDialog extends BasicWidget {
 | 
			
		||||
    doRender() {
 | 
			
		||||
        this.$widget = $(TPL);
 | 
			
		||||
        this.$availableActionList = this.$widget.find(".bulk-available-action-list");
 | 
			
		||||
        this.$existingActionList = this.$widget.find(".bulk-existing-action-list");
 | 
			
		||||
 | 
			
		||||
        this.$widget.on('click', '[data-action-add]', async event => {
 | 
			
		||||
            const actionName = $(event.target).attr('data-action-add');
 | 
			
		||||
 | 
			
		||||
            await bulkActionService.addAction('bulkaction', actionName);
 | 
			
		||||
 | 
			
		||||
            await this.refresh();
 | 
			
		||||
        });
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    async refresh() {
 | 
			
		||||
        this.renderAvailableActions();
 | 
			
		||||
 | 
			
		||||
        const bulkActionNote = await froca.getNote('bulkaction');
 | 
			
		||||
 | 
			
		||||
        const actions = bulkActionService.parseActions(bulkActionNote);
 | 
			
		||||
 | 
			
		||||
        this.$existingActionList.empty();
 | 
			
		||||
 | 
			
		||||
        if (actions.length > 0) {
 | 
			
		||||
            this.$existingActionList.append(...actions.map(action => action.render()));
 | 
			
		||||
        } else {
 | 
			
		||||
            this.$existingActionList.append($("<p>None yet ... add an action by clicking one of the available ones above.</p>"))
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    renderAvailableActions() {
 | 
			
		||||
        this.$availableActionList.empty();
 | 
			
		||||
 | 
			
		||||
        for (const actionGroup of bulkActionService.ACTION_GROUPS) {
 | 
			
		||||
            const $actionGroupList = $("<td>");
 | 
			
		||||
            const $actionGroup = $("<tr>")
 | 
			
		||||
                .append($("<td>").text(actionGroup.title + ": "))
 | 
			
		||||
                .append($actionGroupList);
 | 
			
		||||
 | 
			
		||||
            for (const action of actionGroup.actions) {
 | 
			
		||||
                $actionGroupList.append(
 | 
			
		||||
                    $('<button class="btn btn-sm">')
 | 
			
		||||
                        .attr('data-action-add', action.actionName)
 | 
			
		||||
                        .text(action.actionTitle)
 | 
			
		||||
                );
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            this.$availableActionList.append($actionGroup);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    entitiesReloadedEvent({loadResults}) {
 | 
			
		||||
        if (loadResults.getAttributes().find(attr => attr.type === 'label' && attr.name === 'action')) {
 | 
			
		||||
            this.refresh();
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    async bulkActionsEvent({node}) {
 | 
			
		||||
        await this.refresh();
 | 
			
		||||
 | 
			
		||||
        utils.openDialog(this.$widget);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1451,11 +1451,6 @@ export default class NoteTreeWidget extends NoteContextAwareWidget {
 | 
			
		||||
        importDialog.showDialog(node.data.noteId);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    async bulkAssignAttributesCommand({node}) {
 | 
			
		||||
        const bulkAssignAttributesDialog = await import('../dialogs/bulk_assign_attributes.js');
 | 
			
		||||
        bulkAssignAttributesDialog.showDialog(this.getSelectedOrActiveNodes(node));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    forceNoteSyncCommand({node}) {
 | 
			
		||||
        syncService.forceNoteSync(node.data.noteId);
 | 
			
		||||
    }
 | 
			
		||||
 
 | 
			
		||||
@@ -305,4 +305,10 @@ export default class SearchDefinitionWidget extends NoteContextAwareWidget {
 | 
			
		||||
 | 
			
		||||
        toastService.showMessage('Actions have been executed.', 3000);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    entitiesReloadedEvent({loadResults}) {
 | 
			
		||||
        if (loadResults.getAttributes().find(attr => attr.type === 'label' && attr.name === 'action')) {
 | 
			
		||||
            this.refresh();
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -1,13 +1,32 @@
 | 
			
		||||
<style>
 | 
			
		||||
    #bulk-assign-attributes-dialog .modal-body h4:not(:first-child) {
 | 
			
		||||
        margin-top: 20px;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    #bulk-available-action-list button {
 | 
			
		||||
        padding: 2px 7px;
 | 
			
		||||
        margin-right: 10px;
 | 
			
		||||
        margin-bottom: 5px;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    #bulk-existing-action-list {
 | 
			
		||||
        width: 100%;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    #bulk-existing-action-list td {
 | 
			
		||||
        padding: 7px;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    #bulk-existing-action-list .button-column {
 | 
			
		||||
        /* minimal width so that table remains static sized and most space remains for middle column with settings */
 | 
			
		||||
        width: 50px;
 | 
			
		||||
        white-space: nowrap;
 | 
			
		||||
        text-align: right;
 | 
			
		||||
    }
 | 
			
		||||
</style>
 | 
			
		||||
 | 
			
		||||
<div id="bulk-assign-attributes-dialog" class="modal mx-auto" tabindex="-1" role="dialog">
 | 
			
		||||
    <div class="modal-dialog modal-lg" style="max-width: 1000px" role="document">
 | 
			
		||||
    <div class="modal-dialog modal-xl" role="document">
 | 
			
		||||
        <div class="modal-content">
 | 
			
		||||
            <div class="modal-header">
 | 
			
		||||
                <h5 class="modal-title mr-auto">Bulk assign attributes</h5>
 | 
			
		||||
@@ -17,7 +36,7 @@
 | 
			
		||||
                </button>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div class="modal-body">
 | 
			
		||||
                Affected notes: <span id="affected-note-count">0</span>
 | 
			
		||||
                <h4>Affected notes: <span id="affected-note-count">0</span></h4>
 | 
			
		||||
 | 
			
		||||
                <div class="form-check">
 | 
			
		||||
                    <input class="form-check-input" type="checkbox" value="" id="include-descendants">
 | 
			
		||||
@@ -26,11 +45,13 @@
 | 
			
		||||
                    </label>
 | 
			
		||||
                </div>
 | 
			
		||||
 | 
			
		||||
                Available actions:
 | 
			
		||||
                <h4>Available actions</h4>
 | 
			
		||||
 | 
			
		||||
                <table id="bulk-available-action-list"></table>
 | 
			
		||||
 | 
			
		||||
                <div id="bulk-existing-action-list"></div>
 | 
			
		||||
                <h4>Chosen actions</h4>
 | 
			
		||||
 | 
			
		||||
                <table id="bulk-existing-action-list"></table>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div class="modal-footer">
 | 
			
		||||
                <button type="submit" class="btn btn-primary">Execute bulk actions</button>
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user