### Install Painterro with npm
Source: https://github.com/devforth/painterro/blob/master/README.md
Install Painterro using npm in a JavaScript project.
```bash
npm install painterro --save
```
--------------------------------
### Start hot-reload dev server
Source: https://github.com/devforth/painterro/blob/master/README.md
Run this command to start the hot-reload development server for Painterro. After starting, open http://localhost:3000 to view the demo page.
```bash
npm run dev
```
--------------------------------
### Install Painterro dependencies
Source: https://github.com/devforth/painterro/blob/master/README.md
Installs Node modules after cloning the repository. All build configurations are included in the repo.
```bash
cd painterro
npm ci
```
--------------------------------
### Install Node.js 16 with nvm
Source: https://github.com/devforth/painterro/blob/master/README.md
Commands to install and use Node.js version 16, which is the latest supported version for Painterro development.
```bash
nvm install 16
nvm use 16
```
--------------------------------
### Watch build for Painterro source
Source: https://github.com/devforth/painterro/blob/master/README.md
Run this command in the Painterro source folder to start a watch build, which automatically rebuilds the library when you make changes.
```bash
watch npm run build
```
--------------------------------
### Install eslint-plugin-import
Source: https://github.com/devforth/painterro/blob/master/README.md
Install the eslint-plugin-import package, required when your side app uses ESLint and you want to edit Painterro source from a webpack app.
```bash
npm i eslint-plugin-import
```
--------------------------------
### Painterro colorScheme configuration example
Source: https://github.com/devforth/painterro/blob/master/README.md
Configures Painterro UI colors by passing a colorScheme object to the Painterro constructor. The example sets the main panel color to light-yellow and control color to a custom orange.
```javascript
Painterro({
colorScheme: {
main: '#fdf6b8', // make panels light-yellow
control: '#FECF67' // change controls color
}
}).show()
```
--------------------------------
### Set language for Painterro
Source: https://github.com/devforth/painterro/blob/master/README.md
Pass a language parameter to set the UI language. Example uses Spanish ('es').
```javascript
Painterro({
language: 'es' // Spanish
}).show()
```
--------------------------------
### Scale to fill width and height
Source: https://github.com/devforth/painterro/blob/master/README.md
Scale the image to fill the given width and height, potentially cropping. For example, 50x32 becomes 11x15.
```javascript
.doScale({width: 11, height: 15})
```
--------------------------------
### Binary save handler with XMLHttpRequest
Source: https://github.com/devforth/painterro/blob/master/README.md
Example of a save handler that posts image as binary multipart/form-data using raw XMLHttpRequest. Call done(true) to hide Painterro, done(false) to leave it open.
```javascript
var ptro = Painterro({
saveHandler: function (image, done) {
var formData = new FormData();
formData.append('image', image.asBlob());
// you can also pass suggested filename
// formData.append('image', image.asBlob(), image.suggestedFileName());
var xhr = new XMLHttpRequest();
xhr.open('POST', 'http://127.0.0.1:5000/save-as-binary/', true);
xhr.onload = xhr.onerror = function () {
// after saving is done, call done callback
done(true); //done(true) will hide painterro, done(false) will leave opened
};
xhr.send(formData);
}
})
ptro.show();
```
--------------------------------
### Scale to match width
Source: https://github.com/devforth/painterro/blob/master/README.md
Scale the image to match the given width, preserving aspect ratio. For example, 50x32 becomes 100x64.
```javascript
.doScale({width: 100})
```
--------------------------------
### Scale by factor
Source: https://github.com/devforth/painterro/blob/master/README.md
Scale the image by a given factor. For example, 11x12 becomes 22x24.
```javascript
.doScale({ scale: 2 })
```
--------------------------------
### Custom translation strings
Source: https://github.com/devforth/painterro/blob/master/README.md
Pass a translation object to override UI strings. The example sets the name to 'ua' and overrides the 'apply' string.
```javascript
Painterro({
translation: {
name: 'ua',
strings: {
apply: 'Застосувати'
// other strings
}
}
}).show()
```
--------------------------------
### Save as PNG or JPEG based on alpha channel
Source: https://github.com/devforth/painterro/blob/master/README.md
Uses image.hasAlphaChannel() to choose PNG or JPEG format when getting a blob for upload. This optimizes file size by using JPEG when no transparency is present.
```JavaScript
var ptro = Painterro({
saveHandler: function (image, done) {
image.asBlob(image.hasAlphaChannel() ? 'image/png' : 'image/jpeg');
// upload blob
}
})
```
--------------------------------
### Exportable image object structure
Source: https://github.com/devforth/painterro/blob/master/README.md
Structure of the exportable image object passed to event callbacks like onChange and saveHandler. Contains methods to get blob, data URL, suggested file name, alpha channel info, original mime type, width, and height.
```javascript
{
image: {
asBlob: ƒ asBlob(type, quality) // returns blob
asDataURL: ƒ asDataURL(type, quality) // returns e.g. "data:image/jpeg;base64,/9j/4AAQS...."
suggestedFileName: ƒ suggestedFileName(type) // returns string
hasAlphaChannel(): ƒ suggestedFileName() // returns true or false
getOriginalMimeType: ƒ getOriginalMimeType() // e.g. image/jpeg;
getWidth: ƒ getWidth() // integer
getHeight: ƒ getHeight() // integer
}
operationsDone: int // integer
}
```
--------------------------------
### Initialize Painterro with custom configuration
Source: https://github.com/devforth/painterro/blob/master/build/index.html
Creates a Painterro instance with Ukrainian language, custom color scheme, and a save handler, then shows it.
```javascript
window.p = Painterro({
language: 'uk',
backgroundFillColorAlpha: 0,
hideByEsc: true,
colorScheme: {
main: '#8B817A',
control: '#1A1A1A',
controlContent: '#fff',
controlShadow: 'none',
activeControl: '#6F6762',
activeControlContent: '#fff',
hoverControl: '#6F6762',
hoverControlContent: '#fff',
},
//defaultTool : 'brush',
//how_to_paste_actions: ['extend_right'],
/*hiddenTools: [
'select', 'crop', 'pixelize', 'line', 'arrow', 'rect', 'ellipse',
// 'brush',
// 'eraser',
'text', 'rotate', 'resize',
// 'save', 'open',
// 'close',
// 'undo', 'redo',
// 'zoomin',
// 'zoomout',
'bucket', 'clear', 'settings',
],
*/
saveHandler: this._onPainterroSave,
});
window.p.show()
```
--------------------------------
### Show Painterro instance
Source: https://github.com/devforth/painterro/blob/master/README.md
Create and show a Painterro instance.
```javascript
var p = Painterro()
p.show()
```
--------------------------------
### Authenticate and set credentials for publishing
Source: https://github.com/devforth/painterro/blob/master/Release.md
Commands for authenticating and setting environment variables for publishing. First, log in to npm. Then, read the GitHub token from ~/.ghtoken into GH_PASS, and read the WordPress password from ~/.wppassword into WP_PASSWORD.
```bash
npm login
```
```bash
GH_PASS=`cat ~/.ghtoken`
```
```bash
WP_PASSWORD=`cat ~/.wppassword`
```
--------------------------------
### Initialize Painterro with custom color scheme and backplate image
Source: https://github.com/devforth/painterro/blob/master/build/contained.html
Sets up a container element with fixed dimensions and initializes Painterro with a custom color scheme and a background image. The container ID must match the 'id' option in the Painterro call.
```css
html,body,#wrapper { height:100%; margin:0; padding:0; background-color: lightgray; } #conatiner { position: relative; height: 300px; width: 300px; }
```
```javascript
Painterro({ id: 'conatiner', backgroundFillColor: '#eee', backplateImg: 'https://images.pexels.com/photos/3653762/pexels-photo-3653762.jpeg?auto=compress&cs=tinysrgb&dpr=2&h=650&w=940', colorScheme: { main: '#faf', control: '#d5d', activeControl: '#572257', inputBackground: '#cf99ca', } }).show();
```
--------------------------------
### Configure Painterro with parameters
Source: https://github.com/devforth/painterro/blob/master/README.md
Pass configuration parameters to the Painterro constructor.
```js
Painterro({
activeColor: '#00ff00', // default brush color is green
// ... other params here
})
```
--------------------------------
### Import and show Painterro
Source: https://github.com/devforth/painterro/blob/master/README.md
Import Painterro and show the editor in your code.
```js
import Painterro from 'painterro'
...
Painterro().show()
```
--------------------------------
### Build Painterro library
Source: https://github.com/devforth/painterro/blob/master/README.md
Builds the Painterro library, producing four versions of the library. The main result for script import is build/painterro.min.js.
```bash
npm run build
```
--------------------------------
### HTML and CSS layout for Painterro demo
Source: https://github.com/devforth/painterro/blob/master/build/index.html
Sets up the page layout with full-height containers and a flex holder for the editor.
```html
Painterro().show()
```
--------------------------------
### Save to TinyMCE WYSIWYG editor
Source: https://github.com/devforth/painterro/blob/master/README.md
Initializes TinyMCE and Painterro, inserting the captured image as an HTML img tag into the active editor. The done callback hides the editor after insertion.
```JavaScript
tinymce.init({ selector:'textarea', });
var ptro = Painterro({
saveHandler: function (image, done) {
tinymce.activeEditor.execCommand('mceInsertContent', false, '
');
// after saving is done, call done callback
done(true); //done(true) will hide painterro, done(false) will leave opened
}
})
```
--------------------------------
### Integrate Painterro with TinyMCE
Source: https://github.com/devforth/painterro/blob/master/example/templates/paste_to_tinymce.html
Integrates Painterro with TinyMCE. The first block initializes TinyMCE with a custom button and command that opens Painterro. The second block configures Painterro to insert the edited image into the editor via mceInsertContent when saved.
```javascript
tinymce.init({ selector: 'textarea', plugins: [ 'fullscreen' ], toolbar: 'undo redo | styleselect | bold italic | alignleft aligncenter alignright alignjustify | bullist numlist outdent indent | table | fontsizeselect | painterro', height : "700", setup: function(editor) { editor.addButton("painterro", { title: "Open Painterro", cmd: "painterro_cmd", 'icon': "painterro ptro-icon ptro-icon-painterro", }); //button functionality. editor.addCommand("painterro_cmd", function () { ptro.show(); }); } });
```
```javascript
var ptro = Painterro({
defaultSize: '500x400',
saveHandler: function (image, done) {
tinymce.activeEditor.execCommand('mceInsertContent',false, '
');
done(true)
}
})
```
--------------------------------
### Open Painterro on paste event
Source: https://github.com/devforth/painterro/blob/master/README.md
Listens for paste events, reads the pasted file as a data URL, and opens Painterro with that image. Prevents multiple instances by checking window.painterroOpenedInstance.
```JavaScript
document.onpaste = (event) => {
const { items } = event.clipboardData || event.originalEvent.clipboardData;
Array.from(items).forEach((item) => {
if (item.kind === 'file') {
if (!window.painterroOpenedInstance) {
// if painterro already opened - it will handle onpaste
const blob = item.getAsFile();
const reader = new FileReader();
reader.onload = (readerEvent) => {
window.painterroOpenedInstance = Painterro({
onHide: () => {
window.painterroOpenedInstance = undefined;
},
saveHandler: (image, done) => {
console.log('Save it here', image.asDataURL()); // you could provide your save handler
done(true);
},
}).show(readerEvent.target.result, item.type);
};
reader.readAsDataURL(blob);
}
}
});
};
```
--------------------------------
### Configure Painterro with saveHandler to Upload Base64 Image
Source: https://github.com/devforth/painterro/blob/master/example/templates/paste_as_base64.html
Configures Painterro with a saveHandler that posts the edited image as a base64 data URL to the local server endpoint /save-as-base64/, then reloads the page on success.
```javascript
var ptro = Painterro({
saveHandler: function (image, done) {
var xhr = new XMLHttpRequest()
xhr.open('POST', 'http://127.0.0.1:5000/save-as-base64/')
xhr.setRequestHeader('Content-Type', 'application/json')
xhr.send(JSON.stringify({ image: image.asDataURL('image/png') }))
xhr.onload = function (e) {
done(true)
window.location.reload()
}
}
})
```
--------------------------------
### Include Painterro script tag
Source: https://github.com/devforth/painterro/blob/master/README.md
Include the Painterro script in your HTML head.
```html
```
--------------------------------
### Painterro saveHandler with XHR POST
Source: https://github.com/devforth/painterro/blob/master/README.md
Initializes Painterro with a saveHandler that sends the image as a base64 data URL via XMLHttpRequest to a backend endpoint. The done callback hides or keeps the editor open based on its argument.
```JavaScript
var ptro = Painterro({
saveHandler: function (image, done) {
// of course, instead of raw XHR you can use fetch, jQuery, etc
var xhr = new XMLHttpRequest();
xhr.open("POST", "http://127.0.0.1:5000/save-as-base64/");
xhr.setRequestHeader("Content-Type", "application/json");
xhr.send(JSON.stringify({
image: image.asDataURL()
}));
xhr.onload = function (e) {
// after saving is done, call done callback
done(true); //done(true) will hide painterro, done(false) will leave opened
}
},
activeColor: '#00b400' // change active color to green
});
ptro.show();
```
--------------------------------
### Flask backend for binary save
Source: https://github.com/devforth/painterro/blob/master/README.md
Python Flask backend endpoint that saves the uploaded image file. The same can be implemented with any technology.
```python
@app.route("/save-as-binary/", methods=['POST'])
def binary_saver():
filename = '{:10d}.png'.format(int(time())) # generate some filename
filepath = os.path.join(get_tmp_dir(), filename)
request.files['image'].save(filepath)
return jsonify({})
```
--------------------------------
### Listen for active tool change events
Source: https://github.com/devforth/painterro/blob/master/build/index.html
Adds an event listener to the app element to log when the active tool changes.
```javascript
const el = document.getElementById('app')
el.addEventListener('changeActiveTool',(e)=>{console.log('activeToolHasBeenCHanged',e)})
```
--------------------------------
### Replace import path for Painterro
Source: https://github.com/devforth/painterro/blob/master/README.md
Replace the default import from 'painterro' with the absolute path to the commonjs2 build file in your side app. This allows you to use the source version during development.
```javascript
import Painterro from 'painterro';
```
```javascript
import Painterro from '/home/ivan/devforth/painterro/build/painterro.commonjs2.js';
```
--------------------------------
### Regenerate icons font
Source: https://github.com/devforth/painterro/blob/master/README.md
Run this command to regenerate the icon font after adding or editing icons in the 'res' folder.
```bash
npm run buildfont
```
--------------------------------
### Access Painterro canvas context and commented drawing code
Source: https://github.com/devforth/painterro/blob/master/build/index.html
Retrieves the canvas context from the Painterro instance and includes commented-out drawing and paste handling code.
```javascript
const ctx = window.p.ctx;
// ctx.beginPath();
// ctx.moveTo(0,0);
// ctx.lineTo(300,150);
// ctx.strokeStyle="#FF0000";
// ctx.stroke();
// document.onpaste = (event) => {
// const { items } = event.clipboardData || event.originalEvent.clipboardData;
// Array.from(items).forEach((item) => {
// if (item.kind === 'file') {
// if (!window.painterroOpenedInstance) {
// // if painterro already opened - it will handle onpaste
// const blob = item.getAsFile();
// const reader = new FileReader();
// reader.onload = (readerEvent) => {
// window.painterroOpenedInstance = Painterro({
// initText: 'Press PrtScr, Ctrl+V to paste screenshot.
Press Ctrl+S to save',
// // todo: different for os-es
// onHide: () => {
// window.painterroOpenedInstance = undefined;
// },
// saveHandler: (image, done) => {
// console.log('Save it here', image.asDataURL());
// // you could provide your save handler
// done(true);
// },
// }).show(readerEvent.target.result, item.type);
// };
// reader.readAsDataURL(blob);
// }
// }
// });
// };
```
--------------------------------
### Exclude Painterro from linting in package.json
Source: https://github.com/devforth/painterro/blob/master/README.md
Add this eslintIgnore configuration to your side app's package.json to exclude the compiled Painterro file from linting. Replace the path with your actual Painterro source folder.
```json
"eslintIgnore": [
"/home/ivan/devforth/painterro/build/painterro2.commonjs.js"
],
```
--------------------------------
### Backend endpoint to save base64 image
Source: https://github.com/devforth/painterro/blob/master/README.md
Flask route that receives a base64-encoded image from Painterro, decodes it, and saves it as a PNG file. The image data is expected in the JSON field 'image' with a data URL prefix.
```Python
@app.route("/save-as-base64/", methods=['POST'])
def base64_saver():
filename = '{:10d}.png'.format(int(time())) # generate some filename
filepath = os.path.join(get_tmp_dir(), filename)
with open(filepath, "wb") as fh:
base64_data = request.json['image'].replace('data:image/png;base64,', '')
fh.write(base64.b64decode(base64_data))
return jsonify({})
```
--------------------------------
### Current history state object structure
Source: https://github.com/devforth/painterro/blob/master/README.md
Structure of the current history state object passed to onUndo and onRedo events. Contains prev and next state references, counts, and size information.
```javascript
{
prev: {} or undefined
next: {} or undefined
prevCount: int
sizeh: int
sizew: int
}
```
=== COMPLETE CONTENT === This response contains all available snippets from this library. No additional content exists. Do not make further requests.