Skip to content

Instantly share code, notes, and snippets.

@shawnlau
Created August 7, 2015 00:24
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save shawnlau/57b98a4d10110a74a6ea to your computer and use it in GitHub Desktop.
Save shawnlau/57b98a4d10110a74a6ea to your computer and use it in GitHub Desktop.
/*************************
All of this hotkeyed at the moment. This version only draws with a pen tablet, it won't draw with a mouse. If you are familiar with
the porcessing language, you can edit the mouse functions to take a constant pen pressure.
L loads and image that will go to all 4 layers
B loads and image ( its should be the same dimensions as the other layers) to the active layer.
S saves the active layer. Its flakey right now, the file must exist alreasy for it to be saved.
"+" ( keypad or shift = zooms the image
"-" zooms down
"x" zooms to original size
Hold space key and drag to move image around the window
ALT to pick up a color. Each layer picks up the color for their layer at that location.
"[" makes the pen smaller "]" makes the pen larger.
";" makes the pen more opague " \" " makes the pen less opague
"U" undo's, "R" redos - right now 20 levels
next to add - flip image and a way to work with either pen or mouse.
*/
import codeanticode.tablet.*;
import javax.swing.*;
Tablet tablet;
int numUndo = 20;
int curUndo = 0;
int numLayers = 4;
int undoInstances = 0;
int redoInstances = 0;
PImage img = null;
PGraphics []layers;
PGraphics []uLayers;
PGraphics temp;
int curLayer = 0;
boolean imageSelected = false;
float zoom = 1.0;
float cX = 0; //corner placement
float cY = 0;
float dX = 0.0; //dragged offset
float dY = 0.0;
float rdX = 0.0;
float rdY = 0.0;
float zX = 0;
float zY = 0;
int thickness = 10;
int strength = 50;
int oX = 0; // mouse offset
int oY = 0;
boolean locked = false;
boolean dragging = false;
boolean pickColor = false;
boolean saveUndo = false;
color []penColor;
String info;
void setup() {
info = "Layer: " + curLayer + " Brushsize: " + thickness;
frame.setTitle(info);
tablet = new Tablet(this);
uLayers = new PGraphics[numUndo*numLayers];
layers = new PGraphics[numLayers];
penColor= new color[numLayers];
frame.setResizable(true);
size(600, 600);
noFill();
selectInput("Select a file to process:", "fileSelected");
}
void draw() {
background(100);
if (!imageSelected)
;
else{
layers[curLayer].beginDraw();
layers[curLayer].endDraw();
cornerOffset(); //process the location of the corner x,y
image(layers[curLayer], cX, cY, img.width * zoom, img.height * zoom);
// image(canvas,0,0);
}
ellipse(mouseX,mouseY,thickness*zoom,thickness*zoom);
info = "Layer: " + curLayer + " Brushsize: " + thickness + " Strength: " + strength + " Zoom:" + zoom +" X: " + mouseX + " Y: "+ mouseY
+ " dX: " + dX + " dY: " + dY + " rdX: " + rdX + " rdY: " + rdY;
frame.setTitle(info);
}
void fileSelected(File selection) {
if (selection == null)
println("Window was closed or the user hit cancel.");
else {
img = loadImage( selection.getAbsolutePath());
for(int i = 0; i < numLayers;i++){
layers[i] = createGraphics(img.width,img.height);
layers[i].beginDraw();
layers[i].image(img,0,0);
layers[i].endDraw();
}
temp = createGraphics(img.width,img.height);
temp.beginDraw();
temp.endDraw();
for(int i= 0; i< numUndo * numLayers;i++){
uLayers[i] = createGraphics(img.width,img.height);
uLayers[i].beginDraw();
uLayers[i].endDraw();
}
for(int i = 0; i < numLayers;i++){
layers[i].beginDraw();
layers[i].stroke(0,0,0);
layers[i].strokeWeight(thickness);
layers[i].endDraw();
}
imageSelected = true;
int h = img.height; //process the window size
if(h > (int)((float) displayHeight * 0.9))
h = (int)((float)displayHeight * 0.9);
int w = img.width;
if(w > (int)((float)displayWidth * 0.9))
w = (int)((float)displayWidth * 0.9);
frame.setSize(w,h);
zoom = 1.0;
dX = dY = 0;
}
}
void keyPressed() {
switch(key){
case 'b':
case 'B':
selectInput("Select B image:", "load_B_image");
break;
case 's':
case 'S':
selectInput("SaveLayer", "save_layer");
break;
case 'L':
case 'l':
selectInput("Select a file to process:", "fileSelected");
break;
case 'Z':
case '+':
zoom_up();
break;
case 'z':
case '-':
zoom_down();
break;
case 'X':
case 'x':
zoom = 1.0;
dX =0;
dY = 0;
zX = 0;
zY = 0;
break;
case ' ':
dragging = true;
cursor(MOVE);
break;
case 'u':
case 'U':
undo();
break;
case 'r':
case 'R':
redo();
break;
case ']': thickness++;
set_thickness();
break;
case '[': thickness--;
if(thickness<=0)
thickness = 1;
set_thickness();
break;
case ';':
case ':':
if(strength <10) strength -= 1;
else strength -= (int)(strength *0.1);
if(strength < 1) strength = 1;
break;
case '\'':
case '\"':
if(strength <10)strength+=1;
else strength += (int)(strength * 0.1);
if (strength > 100) strength = 100;
break;
case CODED:
switch(keyCode){
case UP:
if(curLayer < numLayers-1) curLayer++;
break;
case DOWN:
if(curLayer > 0) curLayer--;
break;
case ALT:
pickColor = true;
cursor(HAND);
break;
}
break;
}
info = "Layer: " + curLayer + " Brushsize: " + thickness + " Strength: " + strength +" X: " + mouseX + " Y: "+ mouseY;
frame.setTitle(info);
}
void keyReleased() {
if(dragging){
dragging = false;
cursor(ARROW);
}
else if(pickColor){
pickColor = false;
cursor(ARROW);
}
}
void cornerOffset(){
cX = dX+zX;
cY= dY+zY;
}
void mousePressed() {
//println(mouseX, mouseY, mouseX /zoom, mouseY /zoom);
if(pickColor){
float offsetX = dX+zX;
float offsetY= dY+zY;
for(int i = 0; i < numLayers;i++)
layers[i].beginDraw();
for(int i = 0; i < numLayers;i++){
penColor[i] = layers[i].get((int)((mouseX-offsetX)/zoom), (int)((mouseY-offsetY)/zoom));
layers[i].stroke(penColor[i]);
layers[i].endDraw();
}
}
else if(dragging){
locked = true;
oX= mouseX;
oY=mouseY;
}
else{
save_undo();
float offsetX = dX+zX;
float offsetY= dY+zY;
for(int i = 0; i < numLayers;i++){
layers[i].beginDraw();
layers[i].stroke(penColor[i],strength*tablet.getPressure());
layers[i].line((mouseX-offsetX)/zoom, (mouseY-offsetY)/zoom,
(mouseX-offsetX)/zoom, (mouseY-offsetY)/zoom);
layers[i].endDraw();
}
}
}
void mouseReleased() {
locked = false;
saveUndo = false;
}
void mouseDragged() {
if(!dragging && !pickColor){
for(int i = 0; i< numLayers; i++){
layers[i].beginDraw();
layers[i].stroke(penColor[i],strength*tablet.getPressure());
layers[i].line((pmouseX-(dX+zX))/zoom, (pmouseY-(dY+zY))/zoom,
(mouseX-(dX+zX))/zoom, (mouseY-(dY+zY))/zoom);
layers[i].endDraw();
}
}
else if(locked && dragging) {
dX += mouseX-oX;
dY += mouseY-oY;
rdX= dX /zoom;
rdY = dY / zoom;
oX = mouseX;
oY = mouseY;
}
}
void undo(){
if(undoInstances >0){
if(curUndo == 0)curUndo =numUndo; //wrap around
for(int i = 0; i < numLayers; i++){
println(i * numUndo+curUndo);
layers[i].beginDraw();
layers[i].endDraw(); //seems you need to set the pixels
temp.beginDraw();
temp.image(layers[i],0,0);
temp.endDraw();
layers[i].beginDraw();
layers[i].image(uLayers[i*numUndo+curUndo-1],0,0);
layers[i].endDraw();
uLayers[i*numUndo+curUndo-1].beginDraw();
uLayers[i*numUndo+curUndo-1].image(temp,0,0);
uLayers[i*numUndo+curUndo-1].endDraw();
}
curUndo--;
undoInstances--;
redoInstances++;
}
}
void redo(){
if(redoInstances > 0){
for(int i = 0; i < numLayers;i++){
layers[i].beginDraw();
layers[i].endDraw();
temp.beginDraw();
temp.image(layers[i],0,0);
temp.endDraw();
layers[i].beginDraw();
layers[i].image(uLayers[i*numUndo+curUndo],0,0);
layers[i].endDraw();
uLayers[i*numUndo+curUndo].beginDraw();
uLayers[i*numUndo+curUndo].image(temp,0,0);
uLayers[i*numUndo+curUndo].endDraw();
}
curUndo++;
undoInstances++;
redoInstances--;
if(curUndo == numUndo)
curUndo = 0;
}
}
void save_undo(){
for(int i = 0; i < numLayers;i++){
layers[i].beginDraw();
layers[i].endDraw();
uLayers[i * numUndo +curUndo].beginDraw();
uLayers[i * numUndo + curUndo].image(layers[i],0,0);
uLayers[i * numUndo + curUndo].endDraw();
}
curUndo++;
if(curUndo == numUndo) curUndo = 0;
redoInstances = 0;
undoInstances++;
if(undoInstances>numUndo)undoInstances = numUndo;
println("finished drawing ", curUndo,undoInstances, redoInstances);
}
void set_thickness(){
for(int i = 0; i < numLayers; i++){
layers[i].beginDraw();
layers[i].strokeWeight(thickness);
layers[i].endDraw();
}
}
void zoom_up(){
if (zoom < 10.0){
zoom = zoom+0.5;
dX = rdX * zoom;
dY = rdY * zoom;
zX= (width - width * zoom)/2;
zY = (height - height * zoom)/2;
}
}
void zoom_down(){
if(zoom > 0.5){
zoom = zoom - 0.5;
if(zoom < 0.5) zoom = 0.5;
dX = rdX * zoom;
dY = rdY * zoom;
zX= (width - width * zoom)/2;
zY = (height - height * zoom)/2;
}
// dX=rdX * zoom;
// dY = rdY * zoom;
}
void load_B_image(File selection){
if (selection == null)
;
else {
img = loadImage( selection.getAbsolutePath());
layers[curLayer].beginDraw();
layers[curLayer].image(img,0,0);
layers[curLayer].endDraw();
curUndo = 0;
undoInstances = 0;
redoInstances = 0;
}
}
void save_layer(File selection){
String name= selection.getAbsolutePath();
boolean save = false;
if(selection.exists()){
println("fileExist");
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
}
catch (Exception e) {
e.printStackTrace();
}
String preset= name;
String op1s = JOptionPane.showInputDialog(frame, "File Exists!! Replace?", preset);
if(op1s != null) {
save = true;
name = op1s;
}
}
if(save){
layers[curLayer].beginDraw();
layers[curLayer].save(name);
layers[curLayer].endDraw();
}
}
@shawnlau
Copy link
Author

new code here :https://gist.github.com/shawnlau/cc3eae823fe652f486b8

Newer code coming - I now have a GUI and an alternate view window

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment