Arduino Self-Bondage Controller

Ideas and instructions how you can make your own bondage toys.

Would you consider purchasing a custom circuit board to build your own Self-Bondage Controller?

Poll ended at 26 Mar 2020, 21:46

Yes
12
67%
No
1
6%
Maybe
5
28%
 
Total votes: 18

nelis123
*
Posts: 25
Joined: 30 Dec 2019, 13:29

Re: Arduino Self-Bondage Controller

Post by nelis123 »

Or just add 10 and make them turn off based on the time elapsed (for instance if you plan the session to be 100 mins each 10 mins a led will turn off)
User avatar
Audrey_CD
***
Posts: 224
Joined: 04 Mar 2009, 22:46
Location: United Kingdom

Re: Arduino Self-Bondage Controller

Post by Audrey_CD »

I'd go with this the above. Simple, works for any duration.
Perhaps the odd bug^h^h^h feature that occasionally counts up instead of down... :twisted:

ETA
Riddle wrote:Any suggestions for the LED time indicator? How many LEDs? Is 12 good (6 for minutes, 6 for hours)? Any issue with it being a I2C module using a MCP23017?
That is a very capable chip. I tried to use a PCF8574AN for similar purpose, but the outputs wouldn't drive the MOSFET properly.
User avatar
pavtron
**
Posts: 147
Joined: 19 Dec 2012, 22:38

Re: Arduino Self-Bondage Controller

Post by pavtron »

Riddle wrote:Any suggestions for the LED time indicator?
6 or 10 then just split the time between them.

Could have a mode that makes them longer and longer. So the last one REALLY does take forever to turn off. :twisted:

Or a mode that makes it randomly jump up one or two (without actuality changing the countdown time) just to mess with the viewer. :rofl:
User avatar
Riddle
****
Posts: 1135
Joined: 24 Sep 2008, 08:37
Location: Oregon, USA
Contact:

Re: Arduino Self-Bondage Controller

Post by Riddle »

pavtron wrote:
Riddle wrote:Any suggestions for the LED time indicator?
6 or 10 then just split the time between them.

Could have a mode that makes them longer and longer. So the last one REALLY does take forever to turn off. :twisted:

Or a mode that makes it randomly jump up one or two (without actuality changing the countdown time) just to mess with the viewer. :rofl:
:rofl: Straight binary would do what you want with 10 to 12 LEDs. With 12 LEDs, that last LED is worth 2056 minutes for a total of 68.5 hours.
Resident timer maker. :hi:
Let’s make timers together!
User avatar
Riddle
****
Posts: 1135
Joined: 24 Sep 2008, 08:37
Location: Oregon, USA
Contact:

Re: Arduino Self-Bondage Controller

Post by Riddle »

pavtron wrote:
Riddle wrote:Any suggestions for the LED time indicator?
6 or 10 then just split the time between them.

Could have a mode that makes them longer and longer. So the last one REALLY does take forever to turn off. :twisted:

Or a mode that makes it randomly jump up one or two (without actuality changing the countdown time) just to mess with the viewer. :rofl:
This is the code you are looking for.

Code: Select all

/*  This timer is to time an electromagnet release.
    This version uses the LEDs for the remaining time.
*/
#include <Wire.h>
#include "Adafruit_MCP23017.h"

Adafruit_MCP23017 mcp;

byte hr = 0;
byte mi = 10;
byte sec = 0;
byte start = 0;
byte inByte;

#define OUT A0 // Change in future versions
#define H 1
#define M 2
#define START 0
#define STOP 3
#define M1 4
#define M2 5
#define M3 6
#define M4 7
#define M5 8
#define M6 9
#define H1 10
#define H2 11
#define H3 12
#define H4 13
#define H5 14
#define H6 15



int BB = 300;
long interval = 1000;           // interval at which to blink (milliseconds)
long previousMillis = 0;        // will store last time LED was updated
int ledState = HIGH; 
const int ledPin =  13;      // the number of the LED pin
bool displayFlag = true;
volatile byte displayValue [4] = {0,0,0,0};


void setup() {
  Serial.begin(115200);
  mcp.begin();      // use default address 0
  mcp.pinMode(H, INPUT);
  mcp.pullUp(H, HIGH);  // turn on a 100K pullup internally
  mcp.pinMode(M, INPUT);
  mcp.pullUp(M, HIGH);  // turn on a 100K pullup internally
  mcp.pinMode(START, INPUT);
  mcp.pullUp(START, HIGH);  // turn on a 100K pullup internally
  mcp.pinMode(STOP, INPUT);
  mcp.pullUp(STOP, HIGH);  // turn on a 100K pullup internally
  mcp.pinMode(H1, OUTPUT);
  mcp.pinMode(H2, OUTPUT);
  mcp.pinMode(H3, OUTPUT);
  mcp.pinMode(H4, OUTPUT);
  mcp.pinMode(H5, OUTPUT);
  mcp.pinMode(H6, OUTPUT);
  mcp.pinMode(M1, OUTPUT);
  mcp.pinMode(M2, OUTPUT);
  mcp.pinMode(M3, OUTPUT);
  mcp.pinMode(M4, OUTPUT);
  mcp.pinMode(M5, OUTPUT);
  mcp.pinMode(M6, OUTPUT);
  
  pinMode(ledPin, OUTPUT);
  pinMode(OUT, OUTPUT);
  
  dtest();
}

void loop() {
  check_buttons();
  mills();
  
}


void check_buttons() {
  byte hb = mcp.digitalRead(H);
  byte mb = mcp.digitalRead(M);
  byte stopb = mcp.digitalRead(STOP);
  byte startb = mcp.digitalRead(START);
  
  if(stopb == LOW && start != 0)
    ESTOP();  
  else if(startb == LOW && start == 0) {
    startt();
  }
  else if(hb == LOW && mb == LOW && start == 0) {
    hr = 0;
    mi = 0;
    sec = 0;
    ttime();
    delay(BB);
   }
  else if(hb == LOW && start == 0) {
    hr ++;
    if(hr > 63)  // Change to number of hour LEDs
      hr = 0;
    ttime();
    delay(BB);
    
  }
  else if(mb == LOW && start == 0) {
    mi = mi + 5;
    if(mi > 63)
      mi = 0;
    ttime(); 
    delay(BB);
  }
  else if(stopb == LOW && start == 0) {
     sec = sec + 30;
     if(sec > 30)
       sec = 0;
     ttime(); 
     delay(BB); 
  }
}


void mills() {
    // clock function
   unsigned long currentMillis = millis();
    
  if(currentMillis - previousMillis > interval) {
    cerial();
    // save the last time you blinked the LED 
    previousMillis = currentMillis;
    ledState = !ledState;
    digitalWrite(ledPin, ledState);
    if(start != 0)
      sec --;
    ttime();
  }
} 


void ESTOP() {
  digitalWrite(OUT, LOW);
  start = 0;
  hr = 0;
  mi = 0;
  sec = 0;
  dtest();
  delay(5000);
}

void startt() {
  start = 1;
  long x = sec * 1000;
  sec = 0;
  ttime();
  delay(x);
  digitalWrite(OUT, HIGH);
}


void ttime() {  
  if(hr == 0 && mi == 0 && sec == 0 && start == 1)
      ESTOP();
    else if(sec > 59) {
       if(mi > 0) {
         mi --;
         sec = 59;
       }
       else if (hr > 0 && mi == 0) {
          hr --;
          mi = 59;
          sec = 59;
         }
      }
  byte mcpOut = hr & 0x01;
  mcp.digitalWrite(H1, mcpOut);
  mcpOut = hr & 0x02;
  mcp.digitalWrite(H2, mcpOut);
  mcpOut = hr & 0x04;
  mcp.digitalWrite(H3, mcpOut);
  mcpOut = hr & 0x08;
  mcp.digitalWrite(H4, mcpOut);
  mcpOut = hr & 0x10;
  mcp.digitalWrite(H5, mcpOut);
  mcpOut = hr & 0x20;
  mcp.digitalWrite(H6, mcpOut);

  mcpOut = mi & 0x01;
  mcp.digitalWrite(M1, mcpOut);
  mcpOut = mi & 0x02;
  mcp.digitalWrite(M2, mcpOut);
  mcpOut = mi & 0x04;
  mcp.digitalWrite(M3, mcpOut);
  mcpOut = mi & 0x08;
  mcp.digitalWrite(M4, mcpOut);
  mcpOut = mi & 0x10;
  mcp.digitalWrite(M5, mcpOut);
  mcpOut = mi & 0x20;
  mcp.digitalWrite(M6, mcpOut);
}

void dtest() {
  mcp.digitalWrite(H1, HIGH);
  mcp.digitalWrite(H2, HIGH);
  mcp.digitalWrite(H3, HIGH);
  mcp.digitalWrite(H4, HIGH);
  mcp.digitalWrite(H5, HIGH);
  mcp.digitalWrite(H6, HIGH);
  mcp.digitalWrite(M1, HIGH);
  mcp.digitalWrite(M2, HIGH);
  mcp.digitalWrite(M3, HIGH);
  mcp.digitalWrite(M4, HIGH);
  mcp.digitalWrite(M5, HIGH);
  mcp.digitalWrite(M6, HIGH);
}

void cerial() {
  //the serial stuff goes here.
     // DateTime now = rtc.now();  // Get the time from the RTC IC

   
    Serial.print(hr, DEC);
    Serial.print(':');
    Serial.print(mi, DEC);
    Serial.print(':');
    Serial.print(sec, DEC);
    Serial.println();
   
}
This counts the minutes and hours in binary up to 60 minutes and 63 hours using only 12 LEDs. It is possible with the MCP23017 to use I2C to control 16 LEDs. May I suggest 6 minute LEDs, 5 hour LEDs, and 5 day LEDs for a stupid (31 days, 31 hours, 63 minutes) amount of time?

Adding random errors to the count displayed will take more work...
Resident timer maker. :hi:
Let’s make timers together!
Post Reply