fake brightness adjust (#1845)

* temp

* temp - 1

* next step note

* fix circuit dependency (to fix:can't read p.mem)

* fix circuit dependency (to fix:can't read p.mem)

* notes

* bitmap

* bitmap

* remove my stupid forward declearation

* clean up

* clean up

* level control

* clean up

* clean up

* clean up

* clean up

* format

* format

* format

* format

* format

* fix for comment advices

* fix for comment advices

* fix display issue in notepad app

* slightly increase performance...

* temp for grey_scale and high_constrast

* format

* note for cache implement

* fix for comment request

* fix for comment request
This commit is contained in:
theHallwayThatBringMePassion 2024-02-07 16:07:30 +08:00 committed by GitHub
parent 5eef5b4e31
commit 0370b4eb55
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
15 changed files with 303 additions and 19 deletions

5
.gitignore vendored
View File

@ -55,7 +55,7 @@ CMakeFiles/
# Debugging
.gdbinit*
# Editor/IDE files
# Editor/ IDE files
*.sublime-project
*.sublime-workspace
.vscode
@ -68,8 +68,9 @@ CMakeFiles/
.DS_Store
/firmware/CMakeCache.txt
# Python env
# Python env/ venv
env/
venv/
# Other
*.bak

View File

@ -3,6 +3,7 @@
* Copyright (C) 2016 Furrtek
* Copyright (C) 2023 gullradriel, Nilorea Studio Inc.
* Copyright (C) 2023 Kyle Reed
* Copyleft (ɔ) 2024 zxkmm under GPL license
*
* This file is part of PortaPack.
*
@ -314,6 +315,7 @@ SetUIView::SetUIView(NavigationView& nav) {
&toggle_bias_tee,
&toggle_clock,
&toggle_mute,
&toggle_fake_brightness,
&toggle_sd_card,
&button_save,
&button_cancel});
@ -347,6 +349,7 @@ SetUIView::SetUIView(NavigationView& nav) {
toggle_clock.set_value(!pmem::ui_hide_clock());
toggle_speaker.set_value(!pmem::ui_hide_speaker());
toggle_mute.set_value(!pmem::ui_hide_mute());
toggle_fake_brightness.set_value(!pmem::ui_hide_fake_brightness());
toggle_sd_card.set_value(!pmem::ui_hide_sd_card());
button_save.on_select = [&nav, this](Button&) {
@ -373,6 +376,7 @@ SetUIView::SetUIView(NavigationView& nav) {
pmem::set_ui_hide_clock(!toggle_clock.value());
pmem::set_ui_hide_speaker(!toggle_speaker.value());
pmem::set_ui_hide_mute(!toggle_mute.value());
pmem::set_ui_hide_fake_brightness(!toggle_fake_brightness.value());
pmem::set_ui_hide_sd_card(!toggle_sd_card.value());
send_system_refresh();
@ -747,6 +751,36 @@ void SetConfigModeView::focus() {
button_save.focus();
}
/* FakeBrightnessView ************************************/
SetFakeBrightnessView::SetFakeBrightnessView(NavigationView& nav) {
add_children({&labels,
&field_fake_brightness,
&button_save,
&button_cancel,
&checkbox_brightness_switch});
field_fake_brightness.set_by_value(pmem::fake_brightness_level());
checkbox_brightness_switch.set_value(pmem::apply_fake_brightness());
checkbox_brightness_switch.on_select = [this](Checkbox&, bool v) {
pmem::set_apply_fake_brightness(v);
};
button_save.on_select = [&nav, this](Button&) {
pmem::set_fake_brightness_level(field_fake_brightness.selected_index_value());
nav.pop();
};
button_cancel.on_select = [&nav, this](Button&) {
nav.pop();
};
}
void SetFakeBrightnessView::focus() {
button_save.focus();
}
/* SettingsMenuView **************************************/
SettingsMenuView::SettingsMenuView(NavigationView& nav) {
@ -767,6 +801,7 @@ SettingsMenuView::SettingsMenuView(NavigationView& nav) {
{"SD Card", ui::Color::dark_cyan(), &bitmap_icon_sdcard, [&nav]() { nav.push<SetSDCardView>(); }},
{"User Interface", ui::Color::dark_cyan(), &bitmap_icon_options_ui, [&nav]() { nav.push<SetUIView>(); }},
{"QR Code", ui::Color::dark_cyan(), &bitmap_icon_qr_code, [&nav]() { nav.push<SetQRCodeView>(); }},
{"Brightness", ui::Color::dark_cyan(), &bitmap_icon_brightness, [&nav]() { nav.push<SetFakeBrightnessView>(); }},
});
set_max_rows(2); // allow wider buttons
}

View File

@ -3,6 +3,7 @@
* Copyright (C) 2016 Furrtek
* Copyright (C) 2023 gullradriel, Nilorea Studio Inc.
* Copyright (C) 2023 Kyle Reed
* Copyleft (ɔ) 2024 zxkmm under GPL license
*
* This file is part of PortaPack.
*
@ -320,39 +321,43 @@ class SetUIView : public View {
};
ImageToggle toggle_camera{
{7 * 8, 14 * 16 + 2, 16, 16},
{6 * 8, 14 * 16 + 2, 16, 16},
&bitmap_icon_camera};
ImageToggle toggle_sleep{
{9 * 8, 14 * 16 + 2, 16, 16},
{8 * 8, 14 * 16 + 2, 16, 16},
&bitmap_icon_sleep};
ImageToggle toggle_stealth{
{11 * 8, 14 * 16 + 2, 16, 16},
{10 * 8, 14 * 16 + 2, 16, 16},
&bitmap_icon_stealth};
ImageToggle toggle_converter{
{13 * 8, 14 * 16 + 2, 16, 16},
{12 * 8, 14 * 16 + 2, 16, 16},
&bitmap_icon_upconvert};
ImageToggle toggle_bias_tee{
{15 * 8, 14 * 16 + 2, 16, 16},
{14 * 8, 14 * 16 + 2, 16, 16},
&bitmap_icon_biast_off};
ImageToggle toggle_clock{
{17 * 8, 14 * 16 + 2, 8, 16},
{16 * 8, 14 * 16 + 2, 8, 16},
&bitmap_icon_clk_ext};
ImageToggle toggle_mute{
{18 * 8, 14 * 16 + 2, 16, 16},
{17 * 8, 14 * 16 + 2, 16, 16},
&bitmap_icon_speaker_and_headphones_mute};
ImageToggle toggle_speaker{
{20 * 8, 14 * 16 + 2, 16, 16},
{19 * 8, 14 * 16 + 2, 16, 16},
&bitmap_icon_speaker_mute};
ImageToggle toggle_fake_brightness{
{21 * 8, 14 * 16 + 2, 16, 16},
&bitmap_icon_brightness};
ImageToggle toggle_sd_card{
{22 * 8, 14 * 16 + 2, 16, 16},
{23 * 8, 14 * 16 + 2, 16, 16},
&bitmap_sd_card_ok};
Button button_save{
@ -672,6 +677,46 @@ class SetConfigModeView : public View {
};
};
using portapack::persistent_memory::fake_brightness_level_options;
class SetFakeBrightnessView : public View {
public:
SetFakeBrightnessView(NavigationView& nav);
void focus() override;
std::string title() const override { return "Brightness"; };
private:
Labels labels{
{{1 * 8, 1 * 16}, "Limits screen brightness", Color::light_grey()},
{{1 * 8, 2 * 16}, "(has a small performance", Color::light_grey()},
{{1 * 8, 3 * 16}, "impact when enabled).", Color::light_grey()},
{{2 * 8, 8 * 16}, "Brightness:", Color::light_grey()},
};
OptionsField field_fake_brightness{
{20 * 8, 8 * 16},
6,
{{"12.5%", fake_brightness_level_options::BRIGHTNESS_12p5},
{"25%", fake_brightness_level_options::BRIGHTNESS_25},
{"50%", fake_brightness_level_options::BRIGHTNESS_50}}};
Checkbox checkbox_brightness_switch{
{1 * 8, 5 * 16},
16,
"Enable brightness adjust"};
Button button_save{
{2 * 8, 16 * 16, 12 * 8, 32},
"Save"};
Button button_cancel{
{16 * 8, 16 * 16, 12 * 8, 32},
"Cancel",
};
};
class SettingsMenuView : public BtnGridView {
public:
SettingsMenuView(NavigationView& nav);

View File

@ -26,6 +26,8 @@
#include "log_file.hpp"
#include "string_format.hpp"
#include "portapack_persistent_memory.hpp"
using namespace portapack;
namespace fs = std::filesystem;
@ -550,6 +552,8 @@ void TextEditorView::open_file(const fs::path& path) {
viewer.set_file(*file_);
}
portapack::persistent_memory::set_apply_fake_brightness(false); // work around to resolve the display issue in notepad app. not elegant i know, so TODO.
refresh_ui();
}

View File

@ -5759,6 +5759,44 @@ static constexpr Bitmap bitmap_icon_thermometer{
{16, 16},
bitmap_icon_thermometer_data};
static constexpr uint8_t bitmap_icon_brightness_data[] = {
0x00,
0x00,
0x80,
0x01,
0x80,
0x01,
0x08,
0x10,
0xC0,
0x03,
0xE0,
0x07,
0xF0,
0x0F,
0xF6,
0x6F,
0xF6,
0x6F,
0xF0,
0x0F,
0xE0,
0x07,
0xC0,
0x03,
0x08,
0x10,
0x80,
0x01,
0x80,
0x01,
0x00,
0x00,
};
static constexpr Bitmap bitmap_icon_brightness{
{16, 16},
bitmap_icon_brightness_data};
} /* namespace ui */
#endif /*__BITMAP_HPP__*/

View File

@ -1,5 +1,7 @@
/*
* Copyright (C) 2015 Jared Boone, ShareBrained Technology, Inc.
* copyleft (ɔ) 2023 zxkmm under GPL license
* Copyright (C) 2023 u-foka
*
* This file is part of PortaPack.
*

View File

@ -1,5 +1,7 @@
/*
* Copyright (C) 2015 Jared Boone, ShareBrained Technology, Inc.
* copyleft (ɔ) 2023 zxkmm under GPL license
* Copyright (C) 2023 u-foka
*
* This file is part of PortaPack.
*

View File

@ -327,6 +327,26 @@ SystemStatusView::SystemStatusView(
refresh();
};
toggle_fake_brightness.on_change = [this, &nav](bool v) {
set_dirty();
pmem::set_apply_fake_brightness(v);
if (nav.is_valid() && v) {
nav.display_modal(
"Brightness",
"You have enabled brightness\n"
"adjustment. Performance\n"
"will be impacted slightly.");
// TODO: refresh interface to prevent reboot requirement
// TODO: increase performance
} else if (!v) {
nav.display_modal(
"Brightness",
"Brightness adjust disabled.");
}
refresh();
};
button_bias_tee.on_select = [this](ImageButton&) {
this->on_bias_tee();
};
@ -348,6 +368,7 @@ SystemStatusView::SystemStatusView(
toggle_speaker.set_value(pmem::config_speaker_disable());
toggle_mute.set_value(pmem::config_audio_mute());
toggle_stealth.set_value(pmem::stealth_mode());
toggle_fake_brightness.set_value(pmem::apply_fake_brightness());
audio::output::stop();
audio::output::update_audio_mute();
@ -369,6 +390,8 @@ void SystemStatusView::refresh() {
// Display "Disable speaker" icon only if AK4951 Codec which has separate speaker/headphone control
if (audio::speaker_disable_supported() && !pmem::ui_hide_speaker()) status_icons.add(&toggle_speaker);
if (!pmem::ui_hide_fake_brightness()) status_icons.add(&toggle_fake_brightness);
if (!pmem::ui_hide_sd_card()) status_icons.add(&sd_card_status_view);
status_icons.update_layout();

View File

@ -264,6 +264,10 @@ class SystemStatusView : public View {
Color::light_grey(),
Color::dark_grey()};
ImageToggle toggle_fake_brightness{
{0, 0, 2 * 8, 1 * 16},
&bitmap_icon_brightness};
SDCardStatusView sd_card_status_view{
{0, 0 * 16, 2 * 8, 1 * 16}};

View File

@ -1,5 +1,6 @@
/*
* Copyright (C) 2014 Jared Boone, ShareBrained Technology, Inc.
* Copyleft (ɔ) 2024 zxkmm under GPL license
*
* This file is part of PortaPack.
*
@ -20,6 +21,7 @@
*/
#include "portapack_io.hpp"
#include "portapack_persistent_memory.hpp"
#include "lpc43xx_cpp.hpp"
using namespace lpc43xx;
@ -75,6 +77,14 @@ void IO::reference_oscillator(const bool enable) {
io_write(1, io_reg);
}
bool IO::get_dark_cover() {
return portapack::persistent_memory::apply_fake_brightness();
}
uint8_t IO::get_brightness() {
return portapack::persistent_memory::fake_brightness_level();
}
uint32_t IO::io_update(const TouchPinsConfig write_value) {
/* Very touchy code to save context of PortaPack data bus while the
* resistive touch pin drive is changed. Order of operations is

View File

@ -1,5 +1,6 @@
/*
* Copyright (C) 2014 Jared Boone, ShareBrained Technology, Inc.
* Copyleft (ɔ) 2024 zxkmm under GPL license
*
* This file is part of PortaPack.
*
@ -30,6 +31,8 @@
#include "gpio.hpp"
#include "ui.hpp"
// #include "portapack_persistent_memory.hpp"
namespace portapack {
class IO {
@ -141,7 +144,10 @@ class IO {
}
}
void lcd_write_pixel(const ui::Color pixel) {
void lcd_write_pixel(ui::Color pixel) {
if (get_dark_cover()) {
darken_color(pixel, get_brightness()); // Darken the pixel color
}
lcd_write_data(pixel.v);
}
@ -149,13 +155,19 @@ class IO {
return lcd_read_data();
}
void lcd_write_pixels(const ui::Color pixel, size_t n) {
void lcd_write_pixels(ui::Color pixel, size_t n) {
if (get_dark_cover()) {
darken_color(pixel, get_brightness()); // Darken the pixel color
}
while (n--) {
lcd_write_data(pixel.v);
}
}
void lcd_write_pixels_unrolled8(const ui::Color pixel, size_t n) {
void lcd_write_pixels_unrolled8(ui::Color pixel, size_t n) {
if (get_dark_cover()) {
darken_color(pixel, get_brightness()); // Darken the pixel color
}
auto v = pixel.v;
n >>= 3;
while (n--) {
@ -172,7 +184,11 @@ class IO {
void lcd_write_pixels(const ui::Color* const pixels, size_t n) {
for (size_t i = 0; i < n; i++) {
lcd_write_pixel(pixels[i]);
ui::Color pixel = pixels[i];
if (get_dark_cover()) {
darken_color(pixel, get_brightness()); // Darken the pixel color
}
lcd_write_pixel(pixel);
}
}
@ -203,6 +219,10 @@ class IO {
return switches_raw;
}
bool get_dark_cover();
uint8_t get_brightness();
// TODO: cache the value ^^ & ^ to increaase performance, need a trigger cuz init doesn't work. And since the constructor is constexpr, we can't use with in class var to cache it. maybe cache from outside somewhere and pass it here as argument.
uint32_t io_update(const TouchPinsConfig write_value);
uint32_t lcd_te() {
@ -314,6 +334,61 @@ class IO {
addr(1); /* Set up for data phase (most likely after a command) */
}
void darken_color(ui::Color& pixel, uint8_t darken_level_shift) {
// TODO: 1. do we need edge control?
// currently didn't see and issue without edge control
// but maybe hurts screen hardware without one?
// TODO: 2. de-color mode for accessibility
// TODO: 3. high contrast mode for accessibility
uint16_t r = (pixel.v >> 11) & 0x1F; // Extract red
uint16_t g = (pixel.v >> 5) & 0x3F; // Extract green
uint16_t b = pixel.v & 0x1F; // Extract blue
r = r >> darken_level_shift; // Darken red
g = g >> darken_level_shift; // Darken green
b = b >> darken_level_shift; // Darken blue
pixel.v = (r << 11) | (g << 5) | b; // Combine back to color, check UI::color for the color layout
}
// void high_contrast(ui::Color& pixel, size_t contrast_level_shift) { // TODO
// uint16_t r = (pixel.v >> 11) & 0x1F;
// uint16_t g = (pixel.v >> 5) & 0x3F;
// uint16_t b = pixel.v & 0x1F;
//
// if ((r << contrast_level_shift) > 0x1F) { // should be slightly smaller, need more obverse...
// r = 0x1F;
// } else {
// r = r << contrast_level_shift;
// }
//
// if ((g << contrast_level_shift) > 0x3F) { // same as above
// g = 0x3F;
// } else {
// g = g << contrast_level_shift;
// }
//
// if ((b << contrast_level_shift) > 0x1F) { // same as above
// b = 0x1F;
// } else {
// b = b << contrast_level_shift;
// }
//
// pixel.v = (r << 11) | (g << 5) | b;
// }
//
// void gray_scale(ui::Color& pixel) { // TODO: the blackwhite not looks right....
// uint16_t r = (pixel.v >> 11) & 0x1F;
// uint16_t g = (pixel.v >> 5) & 0x3F;
// uint16_t b = pixel.v & 0x1F;
//
// uint16_t average = (r + g + b) / 3;
//
// pixel.v = (average << 11) | (average << 5) | average;
// }
void lcd_write_data(const uint32_t value) __attribute__((always_inline)) {
// NOTE: Assumes and DIR=0 and ADDR=1 from command phase.
data_write_high(value); /* Drive high byte */

View File

@ -106,7 +106,7 @@ struct ui_config_t {
bool hide_clock : 1;
bool clock_show_date : 1;
bool clkout_enabled : 1;
bool UNUSED_1 : 1;
bool apply_fake_brightness : 1;
bool stealth_mode : 1;
bool config_login : 1;
bool config_splash : 1;
@ -127,13 +127,13 @@ struct ui_config2_t {
bool hide_sd_card : 1;
bool hide_mute : 1;
bool hide_fake_brightness : 1;
bool UNUSED_1 : 1;
bool UNUSED_2 : 1;
bool UNUSED_3 : 1;
bool UNUSED_4 : 1;
bool UNUSED_5 : 1;
bool UNUSED_6 : 1;
bool UNUSED_7 : 1;
uint8_t PLACEHOLDER_2;
uint8_t PLACEHOLDER_3;
@ -223,7 +223,10 @@ struct data_t {
// Rotary encoder dial sensitivity (encoder.cpp/hpp)
uint16_t encoder_dial_sensitivity : 4;
uint16_t UNUSED_8 : 12;
// fake brightness level (not switch, switch is in another place)
uint16_t fake_brightness_level : 4;
uint16_t UNUSED_8 : 8;
// Headphone volume in centibels.
int16_t headphone_volume_cb;
@ -288,6 +291,7 @@ struct data_t {
frequency_tx_correction(0),
encoder_dial_sensitivity(DIAL_SENSITIVITY_NORMAL),
fake_brightness_level(0),
UNUSED_8(0),
headphone_volume_cb(-600),
misc_config(),
@ -619,6 +623,10 @@ bool stealth_mode() {
return data->ui_config.stealth_mode;
}
bool apply_fake_brightness() {
return data->ui_config.apply_fake_brightness;
}
bool config_login() {
return data->ui_config.config_login;
}
@ -718,6 +726,10 @@ void set_config_backlight_timer(const backlight_config_t& new_value) {
data->ui_config.enable_backlight_timeout = static_cast<uint8_t>(new_value.timeout_enabled());
}
void set_apply_fake_brightness(const bool v) {
data->ui_config.apply_fake_brightness = v;
}
uint32_t pocsag_last_address() {
return data->pocsag_last_address;
}
@ -874,6 +886,9 @@ bool ui_hide_clock() {
bool ui_hide_sd_card() {
return data->ui_config2.hide_sd_card;
}
bool ui_hide_fake_brightness() {
return data->ui_config2.hide_fake_brightness;
}
void set_ui_hide_speaker(bool v) {
data->ui_config2.hide_speaker = v;
@ -904,6 +919,9 @@ void set_ui_hide_clock(bool v) {
void set_ui_hide_sd_card(bool v) {
data->ui_config2.hide_sd_card = v;
}
void set_ui_hide_fake_brightness(bool v) {
data->ui_config2.hide_fake_brightness = v;
}
/* Converter */
bool config_converter() {
@ -993,6 +1011,14 @@ void set_config_dst(dst_config_t v) {
data->dst_config = v;
rtc_time::dst_init();
}
// fake brightness level (switch is in another place)
uint8_t fake_brightness_level() {
return data->fake_brightness_level;
}
void set_fake_brightness_level(uint8_t v) {
data->fake_brightness_level = v;
}
// PMem to sdcard settings
@ -1099,6 +1125,7 @@ bool debug_dump() {
pmem_dump_file.write_line("headphone_volume_cb: " + to_string_dec_int(data->headphone_volume_cb));
pmem_dump_file.write_line("config_mode_storage: 0x" + to_string_hex(data->config_mode_storage, 8));
pmem_dump_file.write_line("dst_config: 0x" + to_string_hex((uint32_t)data->dst_config.v, 8));
pmem_dump_file.write_line("fake_brightness_level: " + to_string_dec_uint(data->fake_brightness_level));
// ui_config bits
const auto backlight_timer = portapack::persistent_memory::config_backlight_timer();
@ -1113,6 +1140,7 @@ bool debug_dump() {
pmem_dump_file.write_line("ui_config hide_clock: " + to_string_dec_uint(data->ui_config.hide_clock));
pmem_dump_file.write_line("ui_config clock_with_date: " + to_string_dec_uint(data->ui_config.clock_show_date));
pmem_dump_file.write_line("ui_config clkout_enabled: " + to_string_dec_uint(data->ui_config.clkout_enabled));
pmem_dump_file.write_line("ui_config apply_fake_brightness: " + to_string_dec_uint(data->ui_config.apply_fake_brightness));
pmem_dump_file.write_line("ui_config stealth_mode: " + to_string_dec_uint(data->ui_config.stealth_mode));
pmem_dump_file.write_line("ui_config config_login: " + to_string_dec_uint(data->ui_config.config_login));
pmem_dump_file.write_line("ui_config config_splash: " + to_string_dec_uint(data->ui_config.config_splash));
@ -1127,6 +1155,7 @@ bool debug_dump() {
pmem_dump_file.write_line("ui_config2 hide_clock: " + to_string_dec_uint(data->ui_config2.hide_clock));
pmem_dump_file.write_line("ui_config2 hide_sd_card: " + to_string_dec_uint(data->ui_config2.hide_sd_card));
pmem_dump_file.write_line("ui_config2 hide_mute: " + to_string_dec_uint(data->ui_config2.hide_mute));
pmem_dump_file.write_line("ui_config2 hide_fake_brightness: " + to_string_dec_uint(data->ui_config2.hide_fake_brightness));
// misc_config bits
pmem_dump_file.write_line("misc_config config_audio_mute: " + to_string_dec_int(config_audio_mute()));

View File

@ -132,6 +132,12 @@ typedef union {
} dst_config_t;
static_assert(sizeof(dst_config_t) == sizeof(uint32_t));
enum fake_brightness_level_options {
BRIGHTNESS_50 = 1,
BRIGHTNESS_25 = 2,
BRIGHTNESS_12p5 = 3, // 12p5 is 12.5
};
namespace cache {
/* Set values in cache to sensible defaults. */
@ -263,6 +269,14 @@ uint16_t clkout_freq();
dst_config_t config_dst();
void set_config_dst(dst_config_t v);
/* Fake brightness */
// switch (if do color change):
bool apply_fake_brightness();
void set_apply_fake_brightness(const bool v);
// level (color change level):
uint8_t fake_brightness_level();
void set_fake_brightness_level(uint8_t v);
/* Recon app */
bool recon_autosave_freqs();
bool recon_autostart_recon();
@ -306,6 +320,7 @@ bool ui_hide_camera();
bool ui_hide_sleep();
bool ui_hide_bias_tee();
bool ui_hide_clock();
bool ui_hide_fake_brightness();
bool ui_hide_sd_card();
void set_ui_hide_speaker(bool v);
void set_ui_hide_mute(bool v);
@ -315,6 +330,7 @@ void set_ui_hide_camera(bool v);
void set_ui_hide_sleep(bool v);
void set_ui_hide_bias_tee(bool v);
void set_ui_hide_clock(bool v);
void set_ui_hide_fake_brightness(bool v);
void set_ui_hide_sd_card(bool v);
// sd persisting settings

Binary file not shown.

After

Width:  |  Height:  |  Size: 292 B

View File

@ -30,7 +30,7 @@ usage_message = """
Usage: <directory>
"""
if len(sys.argv) < 1:
if len(sys.argv) < 2:
print(usage_message)
sys.exit(-1)