-
Notifications
You must be signed in to change notification settings - Fork 0
/
analog_pin.cpp
115 lines (94 loc) · 3.27 KB
/
analog_pin.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
//
// Created by Johannes on 18.07.2020.
//
#include <cairomm/context.h>
#include <har/duino.hpp>
#include "parts.hpp"
using namespace har;
using namespace har::parts;
part duino::parts::analog_pin(part_h offset) {
part pt{ PART[standard_ids::ANALOG_PIN + offset],
text("har:analog_pin"),
traits::BOARD_PART |
traits::INPUT |
traits::OUTPUT |
traits::COLORED,
text("Analog pin") };
add_properties_for_traits(pt, 5.);
pt.remove_entry(of::INT_HANDLER);
pt.remove_entry(of::INT_CONDITION);
pt.delegates.init_relative = [](cell & cl) {
auto & gcl = cl.as_grid_cell();
for (auto dir : direction::cardinal) {
auto & ncl = gcl[dir];
if (ncl.is_placed() && ncl.has(of::NEXT_FREE + 1)) {
cl[of::NEXT_FREE + 1] = ncl[of::NEXT_FREE + 1];
break;
}
}
};
pt.delegates.cycle = [](cell & cl) {
auto & gcl = cl.as_grid_cell();
auto mode = pin_mode(uint_t(cl[of::PIN_MODE]));
switch (mode) {
case pin_mode::TRI_STATE: {
auto out = double_t(gcl[of::POWERING_PIN]);
if (!std::isnan(out)) {
gcl[of::POWERING_PIN] = std::nan("1");
}
auto in = double_t(gcl[of::POWERED_PIN]);
if (!std::isnan(in)) {
gcl[of::POWERED_PIN] = std::nan("1");
}
break;
}
case pin_mode::OUTPUT: {
break;
}
case pin_mode::INPUT: {
auto before = double_t(gcl[of::POWERING_PIN]);
double_t after = 0.;
auto connected = gcl.connected();
for (auto & ccl : connected) {
after += double_t(ccl.cell[of::POWERING_PIN]);
}
after /= connected.size();
if (before != after) {
gcl[of::POWERED_PIN] = after;
}
break;
}
}
};
pt.delegates.draw = [](cell & cl, image_t & im) {
if (im.type() == typeid(ImageType)) {
Cairo::RefPtr<Cairo::Surface> sf = Cairo::ImageSurface::create(Cairo::FORMAT_ARGB32, 256, 256);
auto cr = Cairo::Context::create(sf);
auto & gcl = cl.as_grid_cell();
auto color = color_t(gcl[of::COLOR]);
if (uint_t(cl[DESIGN]) == 1) {
draw_socket(cr, color);
} else {
draw_pin_base(cr, color);
draw_pin_corners(cr, gcl, color);
draw_pin_center(cr);
}
if (gcl.is_placed()) {
draw_voltage(cr, cl, color);
}
im = std::make_tuple(sf, uint_t(256u));
}
};
pt.add_visuals({
of::COLOR,
of::POWERING_PIN,
of::POWERED_PIN,
of::LOW_VOLTAGE,
of::HIGH_VOLTAGE,
of::PIN_MODE,
of::DESIGN
});
pt.add_waking(of::POWERING_PIN);
pt.add_connection_use(direction::PIN, text("Input"));
return pt;
}