OffGridInTheCity
Moderator
- Joined
- Dec 15, 2018
- Messages
- 3,212
Really nice looking work!
Really a great idea!I needed to make custom solar mounting brackets for my Japanese tile roof. You might be able to buy them if your roof allows it, but in my case the rise between my roof decking and the space between the tiles is too small. Here's an example of some of the ones you can buy:
View attachment 33707View attachment 33706
Also, they're expensive (at least here). ($13-16 usd each) I need 20 so I put on my Macgyver hat and bought a bunch of these standard 90deg brackets (bottom of this picture below) and figured out how to bend them without an expensive brake press.
View attachment 33708
The top metal strapping is the template I made by pulling off a tile and bending it to the dimensions I need. Then I made a bulky, poorly designed bender (which I'm not too proud of, but it worked for bending the 4 brackets I needed for my orginal 2 solar panels.)
Here's my new and improved diy brake press build...
1st, I repurposed a bench press adjustable safety catcher.
View attachment 33709
Then off to the hardware store for < $6 usd in metal parts and screws. Using some scrap wood I built this guillotine looking contraption. The flat metal is sandwiched and bolted between two pieces of scrap angle iron I had. I ran the side pieces of wood through a table saw to make cuts to act as guides. I made the bottom piece of wood with two 45degree cuts on the table saw and fitted the 90degree metal piece and screwed it in.
View attachment 33711
I added two guides and a spacer to hold the bracket for the first bend.
View attachment 33712
View attachment 33713
Then a 5Ton bottle jack does all the work.
View attachment 33714
I can turn the bracket around and do the second bend from the opposite side.
Actually, I would have preferred using your method; however, I couldn't find the correct size that would work with my tiles/roof.Really a great idea!And maybe simpler than my method with angle brackets and screws and nuts.
Is it possible for you to make a video of this process?
Hi kje,It's also possible to use treated lumber (wood/plank/barge) as mounting rails for solar panels on the roof like I did.
I made a thread about it for some time ago:
Yeah, mine was made from basically "scrap" metal. Good thing is that I didn't pay for any of it, just had to buy the nuts/bolts to put everything together.I notice @Korishan went metal for his ground array as well![]()
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
/************************Hardware Related Macros************************************/
#define MQ_PIN (0) //define which analog input channel you are going to use
#define RL_VALUE (10) //define the load resistance on the board, in kilo ohms
#define RO_CLEAN_AIR_FACTOR (9.21) //RO_CLEAR_AIR_FACTOR=(Sensor resistance in clean air)/RO,
//which is derived from the chart in datasheet
/***********************Software Related Macros************************************/
#define CALIBARAION_SAMPLE_TIMES (50) //define how many samples you are going to take in the calibration phase
#define CALIBRATION_SAMPLE_INTERVAL (500) //define the time interal(in milisecond) between each samples in the
//cablibration phase
#define READ_SAMPLE_INTERVAL (50) //define how many samples you are going to take in normal operation
#define READ_SAMPLE_TIMES (5) //define the time interal(in milisecond) between each samples in
//normal operation
/**********************Application Related Macros**********************************/
#define GAS_H2 (0)
/*****************************Globals***********************************************/
float H2Curve[3] = {2.3, 0.93,-1.44}; //two points are taken from the curve in datasheet.
//with these two points, a line is formed which is "approximately equivalent"
//to the original curve.
//data format:{ x, y, slope}; point1: (lg200, lg8.5), point2: (lg10000, lg0.03)
float Ro = 10; //Ro is initialized to 10 kilo ohms
// Initialize Youmile LCD (PCF8574T Chip Address: 0x27, 16 characters wide, 2 lines high)
LiquidCrystal_I2C lcd(0x27, 16, 2);
void setup() {
Serial.begin(9600); //UART setup, baudrate = 9600bps
// Initialize the I2C LCD hardware interface
lcd.init();
lcd.backlight();
// Force Hardware I2C clock down to 100 kHz Standard Mode for 5-meter path reliability
Wire.setClock(100000);
// Print start message to the remote LCD display
lcd.setCursor(0, 0);
lcd.print("Calibrating...");
lcd.setCursor(0, 1);
lcd.print("Please wait... ");
Serial.print("Calibrating...\n");
Ro = MQCalibration(MQ_PIN); //Calibrating the sensor. Please make sure the sensor is in clean air
//when you perform the calibration
Serial.print("Calibration is done...\n");
Serial.print("Ro=");
Serial.print(Ro);
Serial.print("kohm");
Serial.print("\n");
// Confirm calibration completeness on the display screen
lcd.clear();
lcd.setCursor(0, 0);
lcd.print("Calib. Complete");
lcd.setCursor(0, 1);
lcd.print("Ro: ");
lcd.print(Ro, 1);
lcd.print(" kohm");
delay(3000); // Hold calibration values on screen briefly before runtime loops
lcd.clear();
}
void loop() {
// Calculate current gas density concentrations
int ppmValue = MQGetGasPercentage(MQRead(MQ_PIN)/Ro, GAS_H2);
// Output telemetry data package to local hardware Serial terminal
Serial.print("H2 Concentration:");
Serial.print(ppmValue);
Serial.print( "ppm" );
Serial.print("\n");
// Update remote LCD over the 5-meter connection link
lcd.setCursor(0, 0);
lcd.print("H2 Concentration");
lcd.setCursor(0, 1);
lcd.print(ppmValue);
lcd.print(" ppm "); // Trailing padding spaces clean up residual numeric remnants
delay(200);
}
/****************** MQResistanceCalculation ****************************************
Input: raw_adc - raw value read from adc, which represents the voltage
Output: the calculated sensor resistance
Remarks: The sensor and the load resistor forms a voltage divider. Given the voltage
across the load resistor and its resistance, the resistance of the sensor
could be derived.
************************************************************************************/
float MQResistanceCalculation(int raw_adc) {
return ( ((float)RL_VALUE*(1023-raw_adc)/raw_adc));
}
/***************************** MQCalibration ****************************************
Input: mq_pin - analog channel
Output: Ro of the sensor
Remarks: This function assumes that the sensor is in clean air. It use
MQResistanceCalculation to calculates the sensor resistance in clean air
and then divides it with RO_CLEAN_AIR_FACTOR. RO_CLEAN_AIR_FACTOR is about
10, which differs slightly between different sensors.
************************************************************************************/
float MQCalibration(int mq_pin) {
int i;
float val=0;
for (i=0;i<CALIBARAION_SAMPLE_TIMES;i++) { //take multiple samples
val += MQResistanceCalculation(analogRead(mq_pin));
delay(CALIBRATION_SAMPLE_INTERVAL);
}
val = val/CALIBARAION_SAMPLE_TIMES; //calculate the average value
val = val/RO_CLEAN_AIR_FACTOR; //divided by RO_CLEAN_AIR_FACTOR yields the Ro
//according to the chart in the datasheet
return val;
}
/***************************** MQRead *********************************************
Input: mq_pin - analog channel
Output: Rs of the sensor
Remarks: This function use MQResistanceCalculation to caculate the sensor resistenc (Rs).
The Rs changes as the sensor is in the different consentration of the target
gas. The sample times and the time interval between samples could be configured
by changing the definition of the macros.
************************************************************************************/
float MQRead(int mq_pin) {
int i;
float rs=0;
for (i=0;i<READ_SAMPLE_TIMES;i++) {
rs += MQResistanceCalculation(analogRead(mq_pin));
delay(READ_SAMPLE_INTERVAL);
}
rs = rs/READ_SAMPLE_TIMES;
return rs;
}
/***************************** MQGetGasPercentage **********************************
Input: rs_ro_ratio - Rs divided by Ro
gas_id - target gas type
Output: ppm of the target gas
Remarks: This function passes different curves to the MQGetPercentage function which
calculates the ppm (parts per million) of the target gas.
************************************************************************************/
int MQGetGasPercentage(float rs_ro_ratio, int gas_id) {
if ( gas_id == GAS_H2) {
return MQGetPercentage(rs_ro_ratio,H2Curve);
}
return 0;
}
/***************************** MQGetPercentage **********************************
Input: rs_ro_ratio - Rs divided by Ro
pcurve - pointer to the curve of the target gas
Output: ppm of the target gas
Remarks: By using the slope and a point of the line. The x(logarithmic value of ppm)
of the line could be derived if y(rs_ro_ratio) is provided. As it is a
logarithmic coordinate, power of 10 is used to convert the result to non-logarithmic
value.
************************************************************************************/
int MQGetPercentage(float rs_ro_ratio, float *pcurve) {
return (pow(10,( ((log(rs_ro_ratio)-pcurve[1])/pcurve[2]) + pcurve[0])));
}
[ /code ]
No right/wrong but I'll be interested to see how you operate and how balance works in the long run. Here's what I'm thinking about.....After reviewing my battery bank plans, I decided to split it into two banks; I ordered another BMS (JIKONG V19 JK-PB2A16S15P V19).
I'll still stack the modules in 7 stacks of 20, just wire them in groups of 10 to made two banks.
A couple reasons for this:
1. If I have a problem with one of the battery banks, I'll still have power from the other one.
2. It will be gentler on the BMSs. I think I figured the BMS could see ~115amps--both charge & load under the original plan. (1 big battery bank). It is rated for 150A, but 60ish amps (with 2 BMSs will be super-gentle on them.)
3. Balancing will be more efficient.
I'm looking forward to getting things up and running too.No right/wrong but I'll be interested to see how you operate and how balance works in the long run. Here's what I'm thinking about.....
I need to balance once every 6 months or so to tighten the max pack difference. Things diverge an extra 30mv or so over 6-9months and I believe my cells to be healthy. In my case, I can use Batrium's Auto-Balance which works thru the charge/discharge voltage range so I don't need to 'top balance'. I can just toggle this on for a couple of weeks, regardless of where I am in the year and don't have to manage reaching top charge to encourage balancing.
My packs (that I balance) are 260ah each and in you're case, with 7 stacks of 10 in parallel it will be something like 10 x 30ah = 300ah 'parallel units' in series?. That's a reasonably hefty set of parallel units in series to balance.
If you post you're operational experiences - e.g. do you balance all the time, what kind of drift (max difference) do you run into, etc... I'll be interested to follow along![]()
| CAT5 Pair | CAT5 Wire Color | LCD Pin Connection | Purpose |
|---|---|---|---|
| Pair 1 | Blue / White-Blue | GND | Common Ground |
| Pair 2 | Orange / White-Orange | 5V / VCC | Power Supply |
| Pair 3 | Green / White-Green | SDA | I2C Data Line |
| Pair 4 | Brown / White-Brown | SCL | I2C Clock Line |
Good luck with that, I never got mine to talk to each other. And yeah, I did the pinout change over. I have a patch panel with punches and that didn't work.I need to be careful about is that the PowMr hybrid inverter connection to the BMS (only the master connection is required)
Curious if you only connected the ground and 2 data lines, or all of them? I read that connecting the other lines even though they aren't used can add noise/interference., I never got mine to talk to each other.