@@ -2,7 +2,7 @@ Tracker.autorun(function () {
|
|||||||
var id = Session.get('controller_id');
|
var id = Session.get('controller_id');
|
||||||
if (id) {
|
if (id) {
|
||||||
Meteor.subscribe("sensor_data", id);
|
Meteor.subscribe("sensor_data", id);
|
||||||
var hamo = Meteor.subscribe("controller_state", id);
|
Meteor.subscribe("controller_state", id);
|
||||||
console.log(hamo);
|
Meteor.subscribe('pictures', id);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -12,6 +12,7 @@
|
|||||||
<div class="col-md-12 chart">
|
<div class="col-md-12 chart">
|
||||||
<div><strong>Otpusni ventil:</strong> {{pretty_valve state.out_valve }}</div>
|
<div><strong>Otpusni ventil:</strong> {{pretty_valve state.out_valve }}</div>
|
||||||
<div><strong>Ulazni ventil/pumpa:</strong> {{pretty_valve state.in_valve }}</div>
|
<div><strong>Ulazni ventil/pumpa:</strong> {{pretty_valve state.in_valve }}</div>
|
||||||
|
<div><strong>Dobavlja sliku:</strong> {{picture_requested state }}</div>
|
||||||
<div><strong>Zadnja komunikacija: {{ last_communication_time }}</strong>
|
<div><strong>Zadnja komunikacija: {{ last_communication_time }}</strong>
|
||||||
</div>
|
</div>
|
||||||
<div><strong>Zadnje zaljevanje: {{ last_out_valve_open }}</strong>
|
<div><strong>Zadnje zaljevanje: {{ last_out_valve_open }}</strong>
|
||||||
|
|||||||
@@ -9,10 +9,13 @@ Template.state_details.helpers({
|
|||||||
return moment(this.time).fromNow();
|
return moment(this.time).fromNow();
|
||||||
},
|
},
|
||||||
last_out_valve_open: function() {
|
last_out_valve_open: function() {
|
||||||
return moment(this.significantEvents.lastOutValveOpen).fromNow();
|
return "";
|
||||||
},
|
},
|
||||||
last_in_valve_open: function() {
|
last_in_valve_open: function() {
|
||||||
return moment(this.significantEvents.lastInValveOpen).fromNow();
|
return "";
|
||||||
|
},
|
||||||
|
picture_requested: function(state) {
|
||||||
|
return (state.picture_requested === 'true') ? 'DA' : 'NE';
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
15
app/client/surveillance.html
Normal file
15
app/client/surveillance.html
Normal file
@@ -0,0 +1,15 @@
|
|||||||
|
<template name="surveillance">
|
||||||
|
<div> </div>
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-md-12 text-center">
|
||||||
|
Fotografisano: {{ picture_time }}
|
||||||
|
<button id="request_new_picture">Zatraži Novu</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="row"> </div>
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-md-12">
|
||||||
|
<img src="{{ picture_src }}" class="img-responsive center-block" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
49
app/client/surveillance.js
Normal file
49
app/client/surveillance.js
Normal file
@@ -0,0 +1,49 @@
|
|||||||
|
function controller_state() {
|
||||||
|
var controllerId = Session.get('controller_id');
|
||||||
|
result = ControllerState.findOne({});
|
||||||
|
if (!result) {
|
||||||
|
result = {}
|
||||||
|
};
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
|
||||||
|
function picture() {
|
||||||
|
var controllerId = Session.get('controller_id');
|
||||||
|
result = Picture.findOne({
|
||||||
|
controller_id: controllerId
|
||||||
|
});
|
||||||
|
console.log("rez je", result);
|
||||||
|
if (!result) {
|
||||||
|
result = {}
|
||||||
|
};
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Template.surveillance.helpers({
|
||||||
|
controller_state: controller_state,
|
||||||
|
picture_src: function() {
|
||||||
|
var picture_base64 = picture().picture_base64;
|
||||||
|
var picture_src = '/images/noImage.png';
|
||||||
|
if (picture_base64) {
|
||||||
|
picture_src = 'data:image/jpeg;charset=utf-8;base64,' + picture_base64;
|
||||||
|
}
|
||||||
|
return picture_src;
|
||||||
|
},
|
||||||
|
picture_time: function() {
|
||||||
|
var picture_entry = picture();
|
||||||
|
if (picture_entry) {
|
||||||
|
return moment(picture_entry.time).fromNow();
|
||||||
|
} else {
|
||||||
|
return "Nikad!";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
Template.surveillance.events({
|
||||||
|
'click #request_new_picture': function() {
|
||||||
|
var controller_id = Session.get('controller_id');
|
||||||
|
Meteor.call('requestNewPicture', controller_id)
|
||||||
|
}
|
||||||
|
});
|
||||||
@@ -4,8 +4,8 @@
|
|||||||
<li role="presentation" class="{{ class_for 'start' }}"><a href="#">Stanje</a></li>
|
<li role="presentation" class="{{ class_for 'start' }}"><a href="#">Stanje</a></li>
|
||||||
<li role="presentation" class="{{ class_for 'weather' }}"><a href="#">Vrijeme</a></li>
|
<li role="presentation" class="{{ class_for 'weather' }}"><a href="#">Vrijeme</a></li>
|
||||||
<li role="presentation" class="{{ class_for 'log' }}"><a href="#">Novosti</a></li>
|
<li role="presentation" class="{{ class_for 'log' }}"><a href="#">Novosti</a></li>
|
||||||
|
<li role="presentation" class="{{ class_for 'surveillance' }}"><a href="#">Videonadzor</a></li>
|
||||||
<li role="presentation" class="controller_selection"> <input type="number" id="controller" name="controller" value="{{ selected_controller }}" min="1" max="99999"> <button id="switch" name="switch">Prebaci</button>
|
<li role="presentation" class="controller_selection"> <input type="number" id="controller" name="controller" value="{{ selected_controller }}" min="1" max="99999"> <button id="switch" name="switch">Prebaci</button>
|
||||||
</li>
|
</li>
|
||||||
</ul>
|
</ul>
|
||||||
|
|
||||||
</template>
|
</template>
|
||||||
|
|||||||
@@ -26,10 +26,12 @@ Template.tabs.events({
|
|||||||
'click .log': function() {
|
'click .log': function() {
|
||||||
Session.set('templateName', 'log');
|
Session.set('templateName', 'log');
|
||||||
},
|
},
|
||||||
|
'click .surveillance': function() {
|
||||||
|
Session.set('templateName', 'surveillance');
|
||||||
|
},
|
||||||
'click .settings': function() {
|
'click .settings': function() {
|
||||||
Session.set('templateName', 'settings');
|
Session.set('templateName', 'settings');
|
||||||
},
|
},
|
||||||
|
|
||||||
'click #switch': function() {
|
'click #switch': function() {
|
||||||
var instance = Template.instance();
|
var instance = Template.instance();
|
||||||
controller_id = instance.$('#controller').val();
|
controller_id = instance.$('#controller').val();
|
||||||
|
|||||||
@@ -1,3 +1,4 @@
|
|||||||
|
|
||||||
SensorData = new Mongo.Collection("sensorData");
|
SensorData = new Mongo.Collection("sensorData");
|
||||||
ControllerState = new Mongo.Collection("controller_states");
|
ControllerState = new Mongo.Collection("controller_states");
|
||||||
|
Picture = new Mongo.Collection("pictures");
|
||||||
|
|||||||
BIN
app/public/images/noImage.png
Normal file
BIN
app/public/images/noImage.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 68 KiB |
@@ -10,7 +10,7 @@ Api.addRoute('sensorData', {
|
|||||||
}, {
|
}, {
|
||||||
post: function() {
|
post: function() {
|
||||||
reactToSensorData(this.bodyParams);
|
reactToSensorData(this.bodyParams);
|
||||||
SensorData.insert({
|
var sensorObject = {
|
||||||
temperatureValue: parseFloat(this.bodyParams.temperatureValue),
|
temperatureValue: parseFloat(this.bodyParams.temperatureValue),
|
||||||
humidityValue: parseFloat(this.bodyParams.humidityValue),
|
humidityValue: parseFloat(this.bodyParams.humidityValue),
|
||||||
tankLevel0: this.bodyParams.tankLevel0,
|
tankLevel0: this.bodyParams.tankLevel0,
|
||||||
@@ -24,7 +24,8 @@ Api.addRoute('sensorData', {
|
|||||||
owner: this.bodyParams.owner,
|
owner: this.bodyParams.owner,
|
||||||
controllerId: this.bodyParams.controllerId,
|
controllerId: this.bodyParams.controllerId,
|
||||||
created_at: new Date()
|
created_at: new Date()
|
||||||
});
|
};
|
||||||
|
SensorData.insert(sensorObject);
|
||||||
return [];
|
return [];
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@@ -47,11 +48,11 @@ reactToSensorData = function(nextSensorReading) {
|
|||||||
|
|
||||||
var shouldStartAutomaticPumping = (!state.in_valve || state.in_valve === 'closed') && ((parseInt(nextSensorReading.tankFull) === 0) && startPumpingLevelReached && (state.out_valve === 'closed' || state.out_valve === 'closing'));
|
var shouldStartAutomaticPumping = (!state.in_valve || state.in_valve === 'closed') && ((parseInt(nextSensorReading.tankFull) === 0) && startPumpingLevelReached && (state.out_valve === 'closed' || state.out_valve === 'closing'));
|
||||||
|
|
||||||
console.log("State: ", state);
|
console.log("State: ", state);
|
||||||
|
|
||||||
var shouldStartPumping = shouldStartAutomaticPumping && config && !config.manualInflow;
|
var shouldStartPumping = shouldStartAutomaticPumping && config && !config.manualInflow;
|
||||||
|
|
||||||
console.log("shouldStartAutomaticPumping: ", shouldStartAutomaticPumping);
|
console.log("shouldStartAutomaticPumping: ", shouldStartAutomaticPumping);
|
||||||
|
|
||||||
console.log("shouldStartPumping: ", shouldStartPumping);
|
console.log("shouldStartPumping: ", shouldStartPumping);
|
||||||
|
|
||||||
@@ -75,11 +76,11 @@ reactToSensorData = function(nextSensorReading) {
|
|||||||
else if (nextSensorReading.stopPumpingAt == 'TANKLEVEL4') stopPumpingLevelReached = (parseInt(nextSensorReading.tankLevel4) === 1)
|
else if (nextSensorReading.stopPumpingAt == 'TANKLEVEL4') stopPumpingLevelReached = (parseInt(nextSensorReading.tankLevel4) === 1)
|
||||||
else stopPumpingLevelReached = false;
|
else stopPumpingLevelReached = false;
|
||||||
|
|
||||||
var shouldStopAutomaticPumping = (state.in_valve === 'open' || state.in_valve === 'opening') && (parseInt(nextSensorReading.tankFull) === 1 || stopPumpingLevelReached || state.out_valve === 'open' || state.out_valve === 'opening');
|
var shouldStopAutomaticPumping = (state.in_valve === 'open' || state.in_valve === 'opening') && (parseInt(nextSensorReading.tankFull) === 1 || stopPumpingLevelReached || state.out_valve === 'open' || state.out_valve === 'opening');
|
||||||
|
|
||||||
var shouldStopPumping = shouldStopAutomaticPumping && config && !config.manualInflow;
|
var shouldStopPumping = shouldStopAutomaticPumping && config && !config.manualInflow;
|
||||||
|
|
||||||
console.log("shouldStopPumping: ", shouldStopPumping);
|
console.log("shouldStopPumping: ", shouldStopPumping);
|
||||||
|
|
||||||
|
|
||||||
if (shouldStopPumping) {
|
if (shouldStopPumping) {
|
||||||
@@ -106,6 +107,7 @@ Api.addRoute('state/:id', {
|
|||||||
'$set': {
|
'$set': {
|
||||||
'state.out_valve': this.bodyParams.out_valve,
|
'state.out_valve': this.bodyParams.out_valve,
|
||||||
'state.in_valve': this.bodyParams.in_valve,
|
'state.in_valve': this.bodyParams.in_valve,
|
||||||
|
'state.picture_requested': this.bodyParams.picture_requested,
|
||||||
'time': new Date(),
|
'time': new Date(),
|
||||||
'set_by': 'client'
|
'set_by': 'client'
|
||||||
}
|
}
|
||||||
@@ -116,10 +118,35 @@ Api.addRoute('state/:id', {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
Api.addRoute('picture/:id', {
|
||||||
|
authRequired: false
|
||||||
|
}, {
|
||||||
|
post: function() {
|
||||||
|
console.log("setting picture", this.bodyParams);
|
||||||
|
return Picture.upsert({
|
||||||
|
controller_id: this.urlParams.id
|
||||||
|
}, {
|
||||||
|
'$set': {
|
||||||
|
'picture_base64': this.bodyParams.picture_base64,
|
||||||
|
'time': new Date()
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
function base64_to_buffer(base64string) {
|
||||||
|
var buf;
|
||||||
|
if (typeof Buffer.from === "function") {
|
||||||
|
buf = Buffer.from(base64string, 'base64');
|
||||||
|
} else {
|
||||||
|
buf = new Buffer(base64string, 'base64');
|
||||||
|
}
|
||||||
|
return buf;
|
||||||
|
}
|
||||||
|
|
||||||
function stateOrDefault(id) {
|
function stateOrDefault(id) {
|
||||||
var stateEntry = ControllerState.findOne({
|
var stateEntry = ControllerState.findOne({
|
||||||
controller_id: id,
|
controller_id: id
|
||||||
});
|
});
|
||||||
|
|
||||||
if (stateEntry === undefined) {
|
if (stateEntry === undefined) {
|
||||||
|
|||||||
@@ -52,6 +52,17 @@ function setInValveTo(controller_id, nextState) {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function requestNewPicture(controller_id) {
|
||||||
|
var state = controller_state(controller_id);
|
||||||
|
ControllerState.update(state._id, {
|
||||||
|
'$set': {
|
||||||
|
'state.picture_requested': 'true',
|
||||||
|
'time': new Date(),
|
||||||
|
'set_by': 'server'
|
||||||
|
}
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
function openInValve(controller_id) {
|
function openInValve(controller_id) {
|
||||||
var state = controller_state(controller_id);
|
var state = controller_state(controller_id);
|
||||||
var config = state.config;
|
var config = state.config;
|
||||||
@@ -174,5 +185,6 @@ Meteor.methods({
|
|||||||
openInValve: openInValve,
|
openInValve: openInValve,
|
||||||
closeInValve: closeInValve,
|
closeInValve: closeInValve,
|
||||||
clearLog: clearLog,
|
clearLog: clearLog,
|
||||||
saveControllerConfig: saveControllerConfig
|
saveControllerConfig: saveControllerConfig,
|
||||||
|
requestNewPicture: requestNewPicture
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -16,3 +16,11 @@ Meteor.publish("controller_state", function(controllerId) {
|
|||||||
controller_id: controllerId
|
controller_id: controllerId
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
|
// This code only runs on the server
|
||||||
|
Meteor.publish("pictures", function(controllerId) {
|
||||||
|
return Picture.find({
|
||||||
|
controller_id: controllerId
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|||||||
@@ -11,6 +11,8 @@ crontab -e -u root
|
|||||||
#enter these lines
|
#enter these lines
|
||||||
*/5 * * * * cd /home/pi/projects/tfm/controller && sh activity.sh
|
*/5 * * * * cd /home/pi/projects/tfm/controller && sh activity.sh
|
||||||
*/30 * * * * /usr/bin/python /home/pi/projects/tfm/controller/network_check.py
|
*/30 * * * * /usr/bin/python /home/pi/projects/tfm/controller/network_check.py
|
||||||
|
*/1 * * * * /usr/bin/python /home/pi/projects/tfm/controller/camera_capture.py
|
||||||
|
*/1 * * * * /usr/bin/python /home/pi/projects/tfm/controller/camera_send.py
|
||||||
```
|
```
|
||||||
|
|
||||||
4. add following lines at the end of /etc/rc.local
|
4. add following lines at the end of /etc/rc.local
|
||||||
@@ -19,3 +21,20 @@ crontab -e -u root
|
|||||||
python /home/pi/projects/tfm/controller/lockdown.py
|
python /home/pi/projects/tfm/controller/lockdown.py
|
||||||
python /home/pi/projects/tfm/controller/dweet.py
|
python /home/pi/projects/tfm/controller/dweet.py
|
||||||
```
|
```
|
||||||
|
|
||||||
|
5. create directory
|
||||||
|
```
|
||||||
|
mkdir -p /mnt/zoblakdata
|
||||||
|
```
|
||||||
|
|
||||||
|
6. add following line to /etc/fstab for ramdisk
|
||||||
|
```
|
||||||
|
tmpfs /mnt/zoblakdata tmpfs nodev,nosuid,size=100M 0 0
|
||||||
|
```
|
||||||
|
|
||||||
|
7. install packages
|
||||||
|
|
||||||
|
```
|
||||||
|
sudo apt-get update
|
||||||
|
sudo apt-get install libav-tools
|
||||||
|
```
|
||||||
|
|||||||
3
controller/camera_capture.py
Normal file
3
controller/camera_capture.py
Normal file
@@ -0,0 +1,3 @@
|
|||||||
|
import drivers.camera as camera
|
||||||
|
|
||||||
|
camera.capture_picture()
|
||||||
16
controller/camera_send.py
Normal file
16
controller/camera_send.py
Normal file
@@ -0,0 +1,16 @@
|
|||||||
|
import drivers.camera as camera
|
||||||
|
import requests
|
||||||
|
import config
|
||||||
|
|
||||||
|
picture_base64 = camera.get_transfer_picture_base64()
|
||||||
|
if picture_base64 is not None:
|
||||||
|
camera.remove_transfer_picture()
|
||||||
|
controller_id = config.CONTROLLER_ID
|
||||||
|
owner = "Controller: %s" % controller_id
|
||||||
|
|
||||||
|
response = requests.post(config.PICTURE_URL + '/' + controller_id, json={
|
||||||
|
"picture_base64": picture_base64
|
||||||
|
})
|
||||||
|
print response
|
||||||
|
|
||||||
|
print picture_base64 is not None
|
||||||
@@ -1,5 +1,3 @@
|
|||||||
|
|
||||||
|
|
||||||
GPIO_PIN_DHT = 4 # BCM
|
GPIO_PIN_DHT = 4 # BCM
|
||||||
SENSORDATA_URL = 'http://agrar.zoblak.com/api/v1.0/sensorData'
|
SENSORDATA_URL = 'http://agrar.zoblak.com/api/v1.0/sensorData'
|
||||||
GPIO_PIN_TANKLEVEL0 = 5 # BCM
|
GPIO_PIN_TANKLEVEL0 = 5 # BCM
|
||||||
@@ -14,4 +12,8 @@ START_PUMPING_AT = 'TANKFULL' # start pumping when this level = 0
|
|||||||
STOP_PUMPING_AT = 'TANKFULL' # stop pumping when this level = 1
|
STOP_PUMPING_AT = 'TANKFULL' # stop pumping when this level = 1
|
||||||
API_BASE_URL = 'http://agrar.zoblak.com/api/v1.0'
|
API_BASE_URL = 'http://agrar.zoblak.com/api/v1.0'
|
||||||
CONTROLLER_ID = '120' # every controller must have a different one
|
CONTROLLER_ID = '120' # every controller must have a different one
|
||||||
STATE_FILE = '/var/run/controller_state'
|
STATE_FILE = '/mnt/zoblakdata/controller_state'
|
||||||
|
PICTURE_TRANSFER_FILE='/mnt/zoblakdata/picture_transfer_ready.jpg'
|
||||||
|
PICTURE_INPUT_FILE='/mnt/zoblakdata/picture.jpg' # must match file in PICTURE_COMMAND
|
||||||
|
PICTURE_COMMAND="""avconv -i rtsp://192.168.5.10:554//user=admin_password=_channel=1_stream=0.sdp -i /home/pi/projects/tfm/controller/zoblakLogo.png -filter_complex "[0:v]drawtext=fontfile=/usr/share/fonts/truetype/dejavu/DejaVuSans-Bold.ttf:fontsize=30:box=1:boxcolor=black@0.75:text='%d\.%m\.%Y\. %H\:%M\:%S':fontcolor=white@0.8: x=10: y=10[text]; [text][1:v]overlay=main_w-overlay_w-5:5 [filtered]" -map "[filtered]" -f image2 -vframes 1 /mnt/zoblakdata/picture.jpg""" # filename must match PICTURE_INPUT_FILE path
|
||||||
|
PICTURE_URL = 'http://agrar.zoblak.com/api/v1.0/picture/'
|
||||||
|
|||||||
0
controller/drivers/__init__.py
Normal file
0
controller/drivers/__init__.py
Normal file
28
controller/drivers/camera/__init__.py
Normal file
28
controller/drivers/camera/__init__.py
Normal file
@@ -0,0 +1,28 @@
|
|||||||
|
import config
|
||||||
|
import os
|
||||||
|
import base64;
|
||||||
|
from shutil import copyfile
|
||||||
|
import sys
|
||||||
|
|
||||||
|
def capture_picture():
|
||||||
|
os.system(config.PICTURE_COMMAND)
|
||||||
|
|
||||||
|
def get_transfer_picture_base64():
|
||||||
|
try:
|
||||||
|
with open(config.PICTURE_TRANSFER_FILE, "rb") as image_file:
|
||||||
|
return base64.b64encode(image_file.read())
|
||||||
|
except:
|
||||||
|
print("Unexpected error:", sys.exc_info()[0])
|
||||||
|
return None
|
||||||
|
|
||||||
|
def remove_transfer_picture():
|
||||||
|
try:
|
||||||
|
os.remove(config.PICTURE_TRANSFER_FILE)
|
||||||
|
except:
|
||||||
|
print("Error removing: ", config.PICTURE_TRANSFER_FILE )
|
||||||
|
|
||||||
|
def make_transfer_picture():
|
||||||
|
try:
|
||||||
|
copyfile(config.PICTURE_INPUT_FILE, config.PICTURE_TRANSFER_FILE)
|
||||||
|
except:
|
||||||
|
print("Error copying: ", config.PICTURE_INPUT_FILE, config.PICTURE_TRANSFER_FILE )
|
||||||
@@ -7,27 +7,27 @@ import RPi.GPIO as GPIO
|
|||||||
|
|
||||||
# Try to read the state of GPIO_PIN_TANKLEVELx and GPIO_PIN_TANKFULL
|
# Try to read the state of GPIO_PIN_TANKLEVELx and GPIO_PIN_TANKFULL
|
||||||
GPIO.setmode(GPIO.BCM)
|
GPIO.setmode(GPIO.BCM)
|
||||||
GPIO.setup(config.GPIO_PIN_TANKLEVEL0, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
|
#GPIO.setup(config.GPIO_PIN_TANKLEVEL0, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
|
||||||
GPIO.setup(config.GPIO_PIN_TANKLEVEL1, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
|
#GPIO.setup(config.GPIO_PIN_TANKLEVEL1, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
|
||||||
GPIO.setup(config.GPIO_PIN_TANKLEVEL2, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
|
#GPIO.setup(config.GPIO_PIN_TANKLEVEL2, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
|
||||||
GPIO.setup(config.GPIO_PIN_TANKLEVEL3, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
|
#GPIO.setup(config.GPIO_PIN_TANKLEVEL3, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
|
||||||
GPIO.setup(config.GPIO_PIN_TANKLEVEL4, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
|
GPIO.setup(config.GPIO_PIN_TANKLEVEL4, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
|
||||||
GPIO.setup(config.GPIO_PIN_TANKFULL, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
|
GPIO.setup(config.GPIO_PIN_TANKFULL, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
|
||||||
|
|
||||||
# tank sensor has inverse logic - 0 when it is full 1 when it is not
|
# tank sensor has inverse logic - 0 when it is full 1 when it is not
|
||||||
# so we are inverting its value here
|
# so we are inverting its value here
|
||||||
tankLevel0 = (GPIO.input(config.GPIO_PIN_TANKLEVEL0) == GPIO.LOW)
|
# tankLevel0 = (GPIO.input(config.GPIO_PIN_TANKLEVEL0) == GPIO.LOW)
|
||||||
tankLevel1 = (GPIO.input(config.GPIO_PIN_TANKLEVEL1) == GPIO.LOW)
|
# tankLevel1 = (GPIO.input(config.GPIO_PIN_TANKLEVEL1) == GPIO.LOW)
|
||||||
tankLevel2 = (GPIO.input(config.GPIO_PIN_TANKLEVEL2) == GPIO.LOW)
|
# tankLevel2 = (GPIO.input(config.GPIO_PIN_TANKLEVEL2) == GPIO.LOW)
|
||||||
tankLevel3 = (GPIO.input(config.GPIO_PIN_TANKLEVEL3) == GPIO.LOW)
|
# tankLevel3 = (GPIO.input(config.GPIO_PIN_TANKLEVEL3) == GPIO.LOW)
|
||||||
tankLevel4 = (GPIO.input(config.GPIO_PIN_TANKLEVEL4) == GPIO.LOW)
|
tankLevel4 = (GPIO.input(config.GPIO_PIN_TANKLEVEL4) == GPIO.LOW)
|
||||||
tankFull = (GPIO.input(config.GPIO_PIN_TANKFULL) == GPIO.LOW)
|
tankFull = (GPIO.input(config.GPIO_PIN_TANKFULL) == GPIO.LOW)
|
||||||
|
|
||||||
GPIO.cleanup()
|
GPIO.cleanup()
|
||||||
print 'Bacva Level0: {}'.format(tankLevel0)
|
# print 'Bacva Level0: {}'.format(tankLevel0)
|
||||||
print 'Bacva Level1: {}'.format(tankLevel1)
|
# print 'Bacva Level1: {}'.format(tankLevel1)
|
||||||
print 'Bacva Level2: {}'.format(tankLevel2)
|
# print 'Bacva Level2: {}'.format(tankLevel2)
|
||||||
print 'Bacva Level3: {}'.format(tankLevel3)
|
# print 'Bacva Level3: {}'.format(tankLevel3)
|
||||||
print 'Bacva Level4: {}'.format(tankLevel4)
|
print 'Bacva Level4: {}'.format(tankLevel4)
|
||||||
print 'Bacva puna: {}'.format(tankFull)
|
print 'Bacva puna: {}'.format(tankFull)
|
||||||
|
|
||||||
@@ -42,6 +42,7 @@ stopPumpingAt = config.STOP_PUMPING_AT
|
|||||||
# to 15 times to get a sensor reading (waiting 2 seconds between each retry).
|
# to 15 times to get a sensor reading (waiting 2 seconds between each retry).
|
||||||
humidity, temperature = Adafruit_DHT.read_retry(SENSOR_TYPE, config.GPIO_PIN_DHT)
|
humidity, temperature = Adafruit_DHT.read_retry(SENSOR_TYPE, config.GPIO_PIN_DHT)
|
||||||
|
|
||||||
|
|
||||||
# Un-comment the line below to convert the temperature to Fahrenheit.
|
# Un-comment the line below to convert the temperature to Fahrenheit.
|
||||||
# temperature = temperature * 9/5.0 + 32
|
# temperature = temperature * 9/5.0 + 32
|
||||||
|
|
||||||
@@ -50,7 +51,13 @@ humidity, temperature = Adafruit_DHT.read_retry(SENSOR_TYPE, config.GPIO_PIN_DHT
|
|||||||
# guarantee the timing of calls to read the sensor).
|
# guarantee the timing of calls to read the sensor).
|
||||||
# If this happens try again!
|
# If this happens try again!
|
||||||
if tankFull is not None:
|
if tankFull is not None:
|
||||||
response = requests.post(config.SENSORDATA_URL, json={"owner": owner, "temperatureValue": temperature, "humidityValue":humidity, "tankLevel0": "1" if tankLevel0 else "0","tankLevel1": "1" if tankLevel1 else "0","tankLevel2": "1" if tankLevel2 else "0","tankLevel3": "1" if tankLevel3 else "0", "tankLevel4": "1" if tankLevel4 else "0", "tankFull": "1" if tankFull else "0",
|
response = requests.post(config.SENSORDATA_URL, json={"owner": owner, "temperatureValue": temperature, "humidityValue":humidity,
|
||||||
|
# "tankLevel0": "1" if tankLevel0 else "0",
|
||||||
|
# "tankLevel1": "1" if tankLevel1 else "0",
|
||||||
|
# "tankLevel2": "1" if tankLevel2 else "0",
|
||||||
|
# "tankLevel3": "1" if tankLevel3 else "0",
|
||||||
|
"tankLevel4": "1" if tankLevel4 else "0",
|
||||||
|
"tankFull": "1" if tankFull else "0",
|
||||||
"startPumpingAt": startPumpingAt,"stopPumpingAt": stopPumpingAt,"controllerId": controller_id
|
"startPumpingAt": startPumpingAt,"stopPumpingAt": stopPumpingAt,"controllerId": controller_id
|
||||||
})
|
})
|
||||||
print 'Temp={0:0.1f}*C'.format(temperature)
|
print 'Temp={0:0.1f}*C'.format(temperature)
|
||||||
|
|||||||
@@ -37,7 +37,10 @@ def sync():
|
|||||||
changer = Changer(local_state, server_state)
|
changer = Changer(local_state, server_state)
|
||||||
current_state = changer.process_change()
|
current_state = changer.process_change()
|
||||||
|
|
||||||
|
print "posting :" + repr(current_state)
|
||||||
|
local.data = current_state
|
||||||
server.post_state(current_state)
|
server.post_state(current_state)
|
||||||
|
local.save()
|
||||||
except:
|
except:
|
||||||
print " panicking safely ! "
|
print " panicking safely ! "
|
||||||
safely_panic()
|
safely_panic()
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
import RPi.GPIO as GPIO
|
import RPi.GPIO as GPIO
|
||||||
import config
|
import config
|
||||||
|
from drivers.camera import make_transfer_picture
|
||||||
|
|
||||||
class Changer(object):
|
class Changer(object):
|
||||||
|
|
||||||
@@ -45,6 +46,8 @@ class Changer(object):
|
|||||||
if in_valve_change is not None:
|
if in_valve_change is not None:
|
||||||
in_valve_change()
|
in_valve_change()
|
||||||
|
|
||||||
|
self.fulfill_picture_request()
|
||||||
|
|
||||||
return self.local_state
|
return self.local_state
|
||||||
|
|
||||||
def open_in_valve(self):
|
def open_in_valve(self):
|
||||||
@@ -63,6 +66,12 @@ class Changer(object):
|
|||||||
GPIO.output(config.GPIO_PIN_OUT_VALVE, GPIO.LOW)
|
GPIO.output(config.GPIO_PIN_OUT_VALVE, GPIO.LOW)
|
||||||
self.local_state['out_valve'] = 'closed'
|
self.local_state['out_valve'] = 'closed'
|
||||||
|
|
||||||
|
def fulfill_picture_request(self):
|
||||||
|
if self.remote_state['picture_requested'] == 'true':
|
||||||
|
make_transfer_picture()
|
||||||
|
self.local_state['picture_requested'] = 'false'
|
||||||
|
|
||||||
|
|
||||||
def validate_states(self):
|
def validate_states(self):
|
||||||
if self.local_state is None or self.remote_state is None:
|
if self.local_state is None or self.remote_state is None:
|
||||||
raise ClassNotReadyException("Both local and remote states must be present!")
|
raise ClassNotReadyException("Both local and remote states must be present!")
|
||||||
|
|||||||
@@ -9,7 +9,8 @@ class File(object):
|
|||||||
self.filename = filename
|
self.filename = filename
|
||||||
|
|
||||||
def present(self):
|
def present(self):
|
||||||
os.path.isfile(self.filename)
|
return os.path.isfile(self.filename)
|
||||||
|
|
||||||
|
|
||||||
def load(self):
|
def load(self):
|
||||||
if self.filename is None:
|
if self.filename is None:
|
||||||
|
|||||||
BIN
controller/zoblakLogo.png
Normal file
BIN
controller/zoblakLogo.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 18 KiB |
Reference in New Issue
Block a user