Jebao Issue on Daylight/Actinic Channel
Re: Jebao Issue on Daylight/Actinic Channel
You need to call any one of these waveforms after the PWMSlope/PWMParabola:
http://forum.reefangel.com/viewtopic.php?f=7&t=2844
http://forum.reefangel.com/viewtopic.php?f=7&t=2844
Roberto.
Re: Jebao Issue on Daylight/Actinic Channel
BTW, this:
is the same as this:
Code: Select all
int heaterOn=InternalMemory.read_int(Mem_I_HeaterTempOn);
int heaterOff=InternalMemory.read_int(Mem_I_HeaterTempOff);
ReefAngel.StandardHeater( Port1,heaterOn,heaterOff );
Code: Select all
ReefAngel.StandardHeater( Port1 );
Roberto.
Re: Jebao Issue on Daylight/Actinic Channel
Yeah, I tried to switch back to using DCPump class and use the other random wave mode in another thread for DCPump wave modes... However, I could never get it to select Else mode, it would only choose DCPump modes...
Reason I want else mode is I like that I am able to adjust the delay range and the offset which I have not been able to figure out with any of the other modes.. It seems that they are all based off the same wave speed and I feel restricted by not being able to really change all of their parameters.
Reason I want else mode is I like that I am able to adjust the delay range and the offset which I have not been able to figure out with any of the other modes.. It seems that they are all based off the same wave speed and I feel restricted by not being able to really change all of their parameters.
Re: Jebao Issue on Daylight/Actinic Channel
rimai wrote:BTW, this:is the same as this:Code: Select all
int heaterOn=InternalMemory.read_int(Mem_I_HeaterTempOn); int heaterOff=InternalMemory.read_int(Mem_I_HeaterTempOff); ReefAngel.StandardHeater( Port1,heaterOn,heaterOff );
Code: Select all
ReefAngel.StandardHeater( Port1 );
Lol.... thank you. I knew there was a simpler way to do it. I was trying to figure it out by looking in the libraries but couldn't. Still trying to learn the depths of your code...
Re: Jebao Issue on Daylight/Actinic Channel
Which is totally fineReEfnWrX wrote:Yeah, I tried to switch back to using DCPump class and use the other random wave mode in another thread for DCPump wave modes... However, I could never get it to select Else mode, it would only choose DCPump modes...
Reason I want else mode is I like that I am able to adjust the delay range and the offset which I have not been able to figure out with any of the other modes.. It seems that they are all based off the same wave speed and I feel restricted by not being able to really change all of their parameters.
That's the beauty of the controller.... You can pick and choose what you want and if you don't like, just change it and come up with a totally different solution
Roberto.
Re: Jebao Issue on Daylight/Actinic Channel
Yes, but I really like the DCPump screen that I now do not get
As well as the DCPump screen in the portal
As well as the DCPump screen in the portal
Re: Jebao Issue on Daylight/Actinic Channel
My bad....
I totally missed the function DCPumpRandMode you mentioned before.
Yeah, if you switch the order, it would work too, just like you said. Disregard my previous comment, because you are indeed using the SineMode inside your function.
If we change the code to put the screen back, you won't be able to achieve the Longpulse during feeding. The waveform for feeding is constant. Other than that, I think it can be changed.
I totally missed the function DCPumpRandMode you mentioned before.
Yeah, if you switch the order, it would work too, just like you said. Disregard my previous comment, because you are indeed using the SineMode inside your function.
If we change the code to put the screen back, you won't be able to achieve the Longpulse during feeding. The waveform for feeding is constant. Other than that, I think it can be changed.
Roberto.
Re: Jebao Issue on Daylight/Actinic Channel
Maybe something like this:
Code: Select all
#include <ReefAngel_Features.h>
#include <Globals.h>
#include <RA_Wifi.h>
#include <Wire.h>
#include <OneWire.h>
#include <Time.h>
#include <DS1307RTC.h>
#include <InternalEEPROM.h>
#include <RA_NokiaLCD.h>
#include <RA_ATO.h>
#include <RA_Joystick.h>
#include <LED.h>
#include <RA_TempSensor.h>
#include <Relay.h>
#include <RA_PWM.h>
#include <Timer.h>
#include <Memory.h>
#include <InternalEEPROM.h>
#include <RA_Colors.h>
#include <RA_CustomColors.h>
#include <Salinity.h>
#include <RF.h>
#include <IO.h>
#include <ORP.h>
#include <AI.h>
#include <PH.h>
#include <WaterLevel.h>
#include <Humidity.h>
#include <DCPump.h>
#include <ReefAngel.h>
////// Place global variable code below here
////// Memory Locations used by all formulas
#define Mem_B_AcclDay 100 // Acclimation Day
#define Mem_B_AcclDuration 101 // Days in Accl Cycle
#define Mem_B_SlopeStart 102 // Slopestart for White and Blue channels
/////// Memory Locations used by Blue Formula
#define Mem_B_AcclStartEndBlue 105 // Acclimation starting Slope end%
#define Mem_B_SlopeEndBlue 106 // slope End%
////// Memory Locations used by White Formula
#define Mem_B_AcclStartEndWhite 110 // Acclimation starting Slope end%
#define Mem_B_SlopeEndWhite 111 // Slope End%
////// Place global variable code above here
void setup()
{
// This must be the first line
ReefAngel.Init(); //Initialize controller
ReefAngel.AddStandardMenu(); // Add Standard Menu
ReefAngel.Use2014Screen(); // Let's use 2014 Screen
///// ReefAngel.AddPHExpansion(); // pH Expansion Module
// Ports toggled in Feeding Mode
ReefAngel.FeedingModePorts = Port5Bit;
// Ports toggled in Water Change Mode
ReefAngel.WaterChangePorts = Port2Bit | Port3Bit | Port4Bit | Port5Bit | Port8Bit;
// Ports toggled when Lights On / Off menu entry selected
ReefAngel.LightsOnPorts = Port2Bit | Port4Bit | Port8Bit;
// Ports turned off when Overheat temperature exceeded
ReefAngel.OverheatShutoffPorts = Port1Bit;
// Use T1 probe as temperature and overheat functions
ReefAngel.TempProbe = T1_PROBE;
ReefAngel.OverheatProbe = T1_PROBE;
// Set the Overheat temperature setting
InternalMemory.OverheatTemp_write( 820 );
// Feeeding and Water Change mode speed
ReefAngel.DCPump.FeedingSpeed=0;
ReefAngel.DCPump.WaterChangeSpeed=0;
ReefAngel.DCPump.UseMemory = false;
ReefAngel.DCPump.DaylightChannel = Sync;
ReefAngel.DCPump.ActinicChannel = None;
// Ports that are always on
ReefAngel.Relay.On( Port3 );
ReefAngel.Relay.On( Port7 );
////// Place additional initialization code below here
//Custom Port Labels
ReefAngel.CustomLabels[0]="Heater";
ReefAngel.CustomLabels[1]="BlueLED";
ReefAngel.CustomLabels[2]="ReturnPump";
ReefAngel.CustomLabels[3]="WhiteLED";
ReefAngel.CustomLabels[4]="KalkATO";
ReefAngel.CustomLabels[5]="CarbPhos";
ReefAngel.CustomLabels[6]="WP40";
ReefAngel.CustomLabels[7]="Refugium";
////// Place additional initialization code above here
}
void loop()
{
int heaterOn=InternalMemory.read_int(Mem_I_HeaterTempOn);
int heaterOff=InternalMemory.read_int(Mem_I_HeaterTempOff);
ReefAngel.StandardHeater( Port1,heaterOn,heaterOff );
ReefAngel.StandardLights( Port2,12,0,22,0 );
ReefAngel.StandardLights( Port4,13,0,21,0 );
ReefAngel.SingleATO( true,Port5,1200,1 );
ReefAngel.StandardLights( Port8,20,30,13,0 );
////// Place your custom code below here
MediaFilter();
LEDschedule();
DCPumpRandMode();
////// Place your custom code above here
// This should always be the last line
ReefAngel.Portal("ReEfnWrX","******");
ReefAngel.ShowInterface();
}
void DCPumpRandMode() {
static unsigned long feeding;
// Set timer when in feeding mode
if (now()%SECS_PER_DAY<36000 || now()%SECS_PER_DAY>=79200) { // 10pm -> 10am
ReefAngel.PWM.SetDaylight( ElseMode(35,0,true) ); // Night mode (go to 30%)
ReefAngel.DCPump.SetMode( Custom,35,0 );
}
else if (now()%SECS_PER_DAY>=36000 && now()%SECS_PER_DAY<79200) {
static byte randMode=2;
if (now()%SECS_PER_DAY==36001 || now()%SECS_PER_DAY==43200 || now()%SECS_PER_DAY==50400 || now()%SECS_PER_DAY==57600 || now()%SECS_PER_DAY==64800 || now()%SECS_PER_DAY==72000) randMode=random(1,8);
if (randMode==1)
{
ReefAngel.PWM.SetDaylight( SineMode(40,75,85,true) );
ReefAngel.DCPump.SetMode( Custom,75,85 );
}
if (randMode==2)
{
ReefAngel.PWM.SetDaylight( ElseMode(60,20,true) );
ReefAngel.DCPump.SetMode( Custom,60,20 );
}
if (randMode==3)
{
ReefAngel.PWM.SetDaylight( SineMode(30,70,180,true) );
ReefAngel.DCPump.SetMode( Custom,70,180 );
}
if (randMode==4)
{
ReefAngel.PWM.SetDaylight( ElseMode(50,15,true) );
ReefAngel.DCPump.SetMode( Custom,50,15 );
}
if (randMode==5)
{
// ReefAngel.PWM.SetDaylight( ReefCrestMode(55,20,true) );
ReefAngel.DCPump.SetMode( ReefCrest,55,20 );
}
if (randMode==6)
{
// ReefAngel.PWM.SetDaylight( LongPulseMode(25,65,60,true) );
ReefAngel.DCPump.SetMode( LongPulse,65,60 );
}
if (randMode==7)
{
// ReefAngel.PWM.SetDaylight( LongPulseMode(40,40,900,true) );
ReefAngel.DCPump.SetMode( LongPulse,40,900 );
}
}
if (ReefAngel.DisplayedMenu==FEEDING_MODE) {
feeding=now();
// ReefAngel.PWM.SetDaylight( LongPulseMode(0,21,60,true) );
}
else if (now()-feeding>0 && now()-feeding<=9000) {
// Continue NTM for the 2.5 hours
// ReefAngel.PWM.SetDaylight( NutrientTransportMode(0,70,400,true) );
ReefAngel.DCPump.SetMode( NutrientTransport,70,400 );
}
}
void MediaFilter() {
if ( (now()%SECS_PER_DAY>0) && (now()%SECS_PER_DAY<=7200) ) {
ReefAngel.Relay.On( Port6 );
}
else if ( (now()%SECS_PER_DAY>=7201) ) {
ReefAngel.Relay.Off( Port6 );
}
}
void LEDschedule() {
////////// LED Dimming Acclimation Cycle and your standard LED schedule
////////// Variables used for all channels
byte acclDay = InternalMemory.read(Mem_B_AcclDay); // What day in the acclimation cycle it is
byte acclDuration = InternalMemory.read(Mem_B_AcclDuration); // Acclimation Duration in days
byte startPercent = InternalMemory.read(Mem_B_SlopeStart); // Normal start% being used by all 3 channels
////////// Blue Channel Variables
byte acclStartEndBlue = InternalMemory.read(Mem_B_AcclStartEndBlue); // Starting End% for Acclimation cycle
float acclendPercentBlue = InternalMemory.read(Mem_B_SlopeEndBlue); // Your target Blue end% once acclimation is complete
////////// Blue Channel Formula
float acclPercentPerDayBlue = (acclendPercentBlue - acclStartEndBlue) / acclDuration; // How much your Blue end% rises per acclimation day
float acclFactorBlue = acclDay * acclPercentPerDayBlue; // endPercentBlue will be offset by this much. If acclDay = 0 then this value will be 0
byte endPercentBlue = acclendPercentBlue - acclFactorBlue; // Your final Blue end% for the day
////////// White Channel Variables
byte acclStartEndWhite = InternalMemory.read(Mem_B_AcclStartEndWhite); // Starting End% for Acclimation cycle
float acclEndPercentWhite = InternalMemory.read(Mem_B_SlopeEndWhite); // Your target White end% once acclimation is complete
////////// White Channel Formula
float acclPercentPerDayWhite= (acclEndPercentWhite - acclStartEndWhite) / acclDuration; // How much your White end% rises per acclimation day
float acclFactorWhite = acclDay * acclPercentPerDayWhite; // endPercentWhite will be offset by this much. If acclDay = 0 then this value will be 0
byte endPercentWhite = acclEndPercentWhite - acclFactorWhite;
////////// Your standard PWM Dimming code using the variables above to determine start% and end%
ReefAngel.PWM.SetChannel( 0, PWMSlope(13,0,21,0,startPercent,endPercentWhite,60,25) );
ReefAngel.PWM.SetChannel( 1, PWMSlope(12,0,22,0,startPercent,endPercentBlue,120,25) );
ReefAngel.PWM.SetChannel( 2, PWMSlope(12,0,22,0,startPercent,endPercentBlue,120,25) );
////////// At the end of the day, we need to decrement the acclimation counter.
static boolean acclCounterReady=false; // We need a boolean so we only do this once per day
if (now()%SECS_PER_DAY!=0) acclCounterReady=true; // If it's not midnight we'll get the boolean ready
if (now()%SECS_PER_DAY==0 && acclCounterReady && acclDay>0) { // It's midnight, our bool is true and acclDay is more than 0
acclDay--; // Reduce the counter
acclCounterReady=false; // Reset the boolean flag
InternalMemory.write(Mem_B_AcclDay,acclDay); // Update memory
}
}
byte ElseMode( byte MidPoint, byte Offset, boolean WaveSync )
{
////////// Static's only initialize the first time they are called
static unsigned long LastChange=millis(); // Set the inital time that the last change occurred
static int Delay = random(2000,3000); // Set the initial delay - default 500, 3000
static int NewSpeed = MidPoint; // Set the initial speed
static int AntiSpeed = MidPoint; // Set the initial anti sync speed
if ((millis()-LastChange) > Delay) // Check if the delay has elapsed
{
Delay=random(2000,10000); // If so, come up with a new delay - default - 500, 5000
int ChangeUp = random(Offset); // Amount to go up or down
if (random(100)<50) // 50/50 chance of speed going up or going down
{
NewSpeed = MidPoint - ChangeUp;
AntiSpeed = MidPoint + ChangeUp;
}
else
{
NewSpeed = MidPoint + ChangeUp;
AntiSpeed = MidPoint - ChangeUp;
}
LastChange=millis(); // Reset the time of the last change
}
if (WaveSync)
{
return NewSpeed;
}
else
{
return AntiSpeed;
}
}
Roberto.
Re: Jebao Issue on Daylight/Actinic Channel
I switched the Function order to
And when I turn on the Relay port for the LED's it still overrides the Daylight channel to internal memory.
Maybe this is because the random mode selected was Else mode... and not one of the other's that are defined in the libraries.
Code: Select all
MediaFilter();
LEDschedule();
DCPumpRandMode();
Maybe this is because the random mode selected was Else mode... and not one of the other's that are defined in the libraries.
Re: Jebao Issue on Daylight/Actinic Channel
I know why....
When the time is for ElseMode, the LightsOverride variable is set to true because it is not one of the default wave patterns... So, you still need to call the dummy waveform just to ensure we are always calling it.
When the time is for ElseMode, the LightsOverride variable is set to true because it is not one of the default wave patterns... So, you still need to call the dummy waveform just to ensure we are always calling it.
Roberto.
Re: Jebao Issue on Daylight/Actinic Channel
So I see in the globals.cpp that the wave mode codes have this
Could I just add this into my byte elsemode code? That should end the problem?
Code: Select all
LightsOverride=false;
Last edited by ReEfnWrX on Sat Jan 25, 2014 12:09 pm, edited 1 time in total.