select drive based on arrow keys

This commit is contained in:
Hendrik Schutter 2020-08-07 11:38:00 +02:00
parent a92a9c2a2a
commit 1b0ea97ed1
7 changed files with 355 additions and 267 deletions

View File

@ -50,7 +50,7 @@ public:
private:
vector <Drive> vecDrives; //stores all drive data
static void searchDrives(vector <Drive>* pvecDrives);
static void printDrives(vector <Drive>* pvecDrives);
@ -59,9 +59,10 @@ private:
static void ThreadScannDevices();
static void ThreadUserInput();
void filterNewDrives(vector <Drive>* pvecOldDrives, vector <Drive>* pvecNewDrives);
static void handleArrowKey(TUI::UserInput userInput);
static void filterNewDrives(vector <Drive>* pvecOldDrives, vector <Drive>* pvecNewDrives);
TUI *ui;

View File

@ -13,6 +13,7 @@
#define COLOR_AREA_STDSCR 1
#define COLOR_AREA_OVERVIEW 2
#define COLOR_AREA_ENTRY 3
#define COLOR_AREA_ENTRY_SELECTED 4
#define COLOR_GRAY 8
@ -28,7 +29,7 @@ public:
static void initTUI();
void updateTUI(vector <Drive>* pvecDrives);
void updateTUI(vector <Drive>* pvecDrives, int32_t i32SelectedEntry);
static enum UserInput readUserInput();
@ -43,7 +44,7 @@ private:
static void centerTitle(WINDOW *pwin, const char * title);
static WINDOW *createOverViewWindow( int iXSize, int iYSize);
static WINDOW *createDetailViewWindow( int iXSize, int iYSize, int iXStart);
static WINDOW *createEntryWindow(int iXSize, int iYSize, int iXStart, int iYStart,string sModelFamily, string sModelName, string sCapacity);
static WINDOW *createEntryWindow(int iXSize, int iYSize, int iXStart, int iYStart,string sModelFamily, string sModelName, string sCapacity, bool bSelected);
};

View File

@ -8,7 +8,8 @@
#include "../../include/reHDD.h"
TUI::TUI(void) {
TUI::TUI(void)
{
@ -26,9 +27,12 @@ void TUI::initTUI()
initscr();
raw();
keypad(stdscr,TRUE);
if(has_colors() == TRUE) {
if(has_colors() == TRUE)
{
start_color();
} else {
}
else
{
printf("Your terminal does not support color\n");
exit(1);
}
@ -41,11 +45,18 @@ void TUI::initTUI()
init_pair(COLOR_AREA_STDSCR,COLOR_WHITE, COLOR_BLUE);
wbkgd(stdscr, COLOR_PAIR(COLOR_AREA_STDSCR));
init_pair(COLOR_AREA_ENTRY, COLOR_BLACK, COLOR_GRAY);
init_pair(COLOR_AREA_ENTRY_SELECTED, COLOR_BLACK, COLOR_WHITE);
init_pair(COLOR_AREA_OVERVIEW, COLOR_BLACK, COLOR_GRAY);
init_pair(COLOR_AREA_OVERVIEW, COLOR_BLACK, COLOR_GRAY);
mvprintw(0, 2, "reHDD - HDD refurbishing tool - GPL 3.0 ");
}
void TUI::updateTUI(vector <Drive>* pvecDrives) {
void TUI::updateTUI(vector <Drive>* pvecDrives, int32_t i32SelectedEntry)
{
int stdscrX, stdscrY;
getmaxyx(stdscr, stdscrY, stdscrX);
@ -68,12 +79,20 @@ void TUI::updateTUI(vector <Drive>* pvecDrives) {
string sModelName = it->getModelName();
string sCapacity = it->sCapacityToText();
WINDOW * tmp = createEntryWindow( ((int)(stdscrX/3) - 2), 5, 3, (5* (it - pvecDrives->begin()) )+3, sModelFamily, sModelName, sCapacity);
bool bSelectedEntry = false;
if(i32SelectedEntry == (it - pvecDrives->begin()))
{
bSelectedEntry = true;
}
WINDOW * tmp = createEntryWindow( ((int)(stdscrX/3) - 2), 5, 3, (5* (it - pvecDrives->begin()) )+3, sModelFamily, sModelName, sCapacity, bSelectedEntry);
wrefresh(tmp);
}
}
enum TUI::UserInput TUI::readUserInput() {
enum TUI::UserInput TUI::readUserInput()
{
int ch = wgetch(stdscr);
switch(ch)
{
@ -106,7 +125,8 @@ enum TUI::UserInput TUI::readUserInput() {
}
void TUI::centerTitle(WINDOW *pwin, const char * title) {
void TUI::centerTitle(WINDOW *pwin, const char * title)
{
int x, maxX, stringSize;
getmaxyx(pwin, maxX, maxX);
stringSize = 4 + strlen(title);
@ -118,10 +138,11 @@ void TUI::centerTitle(WINDOW *pwin, const char * title) {
waddch(pwin, ACS_LTEE);
}
WINDOW* TUI::createOverViewWindow( int iXSize, int iYSize) {
WINDOW* TUI::createOverViewWindow( int iXSize, int iYSize)
{
WINDOW *newWindow;
newWindow = newwin(iYSize, iXSize, 2, 2);
init_pair(COLOR_AREA_OVERVIEW, COLOR_BLACK, COLOR_GRAY);
wbkgd(newWindow, COLOR_PAIR(COLOR_AREA_OVERVIEW));
box(newWindow, ACS_VLINE, ACS_HLINE);
@ -142,10 +163,11 @@ WINDOW* TUI::createOverViewWindow( int iXSize, int iYSize) {
return newWindow;
}
WINDOW* TUI::createDetailViewWindow( int iXSize, int iYSize, int iXStart) {
WINDOW* TUI::createDetailViewWindow( int iXSize, int iYSize, int iXStart)
{
WINDOW *newWindow;
newWindow = newwin(iYSize, iXSize, 2, iXStart);
init_pair(COLOR_AREA_OVERVIEW, COLOR_BLACK, COLOR_GRAY);
wbkgd(newWindow, COLOR_PAIR(COLOR_AREA_OVERVIEW));
box(newWindow, ACS_VLINE, ACS_HLINE);
centerTitle(newWindow, "Selected Drive: xyz");
@ -154,14 +176,27 @@ WINDOW* TUI::createDetailViewWindow( int iXSize, int iYSize, int iXStart) {
return newWindow;
}
WINDOW* TUI::createEntryWindow(int iXSize, int iYSize, int iXStart, int iYStart, string sModelFamily, string sModelName, string sCapacity) {
WINDOW* TUI::createEntryWindow(int iXSize, int iYSize, int iXStart, int iYStart, string sModelFamily, string sModelName, string sCapacity, bool bSelected)
{
WINDOW *newWindow;
newWindow = newwin(iYSize, iXSize, iYStart, iXStart);
init_pair(COLOR_AREA_ENTRY, COLOR_BLACK, COLOR_GRAY);
wbkgd(newWindow, COLOR_PAIR(COLOR_AREA_ENTRY));
box(newWindow, ACS_VLINE, ACS_HLINE);
if(!bSelected)
{
// entry is NOT selected
attron(COLOR_PAIR(COLOR_AREA_ENTRY));
wbkgd(newWindow, COLOR_PAIR(COLOR_AREA_ENTRY));
}
else
{
// entry IS selected
attron(COLOR_PAIR(COLOR_AREA_ENTRY));
wbkgd(newWindow, COLOR_PAIR(COLOR_AREA_ENTRY_SELECTED));
}
box(newWindow, ACS_VLINE, ACS_HLINE);
mvwaddstr(newWindow,1, 1, sModelFamily.c_str());
mvwaddstr(newWindow,2, 1, sModelName.c_str());

View File

@ -46,12 +46,15 @@ uint32_t Drive::getPowerCycles(void)
return u32PowerCycles;
}
string Drive::sCapacityToText() {
if(getCapacity() <= (999*1000000000UL)) {
string Drive::sCapacityToText()
{
if(getCapacity() <= (999*1000000000UL))
{
// Less or even 999 GB --> GB
return to_string(getCapacity() / 1000000000UL) + " GB";
}
else {
else
{
// More 999 GB --> TB
return to_string(getCapacity() / 1000000000000UL) + " TB";
}

View File

@ -18,6 +18,11 @@ static std::mutex mxScannDrives;
static vector <Drive> vecNewDrives; //store found drives that are updated every 5sec
static vector <Drive> vecDrives; //stores all drive data from scann thread
TUI *ui;
static int32_t i32SelectedEntry;
static fd_set selectSet;
@ -29,8 +34,7 @@ static fd_set selectSet;
reHDD::reHDD(void)
{
cout << "created app" << endl;
i32SelectedEntry = 0;
}
/**
@ -41,9 +45,7 @@ reHDD::reHDD(void)
void reHDD::app_logic(void)
{
cout << "app logic" << endl;
ui = new TUI();
ui->initTUI();
pipe(fdSearchDrives);
@ -56,32 +58,41 @@ void reHDD::app_logic(void)
thread thDevices(ThreadScannDevices); //start thread that scanns for drives
thread thUserInput(ThreadUserInput); //start thread that reads user input
while(1) {
while(1)
{
select(FD_SETSIZE, &selectSet, NULL, NULL, NULL);
if( FD_ISSET(fdSearchDrives[0], &selectSet)) {
if( FD_ISSET(fdSearchDrives[0], &selectSet))
{
char dummy;
read (fdSearchDrives[0],&dummy,1);
mxScannDrives.lock();
filterNewDrives(&vecDrives, &vecNewDrives);
filterNewDrives(&vecDrives, &vecNewDrives); //filter and copy to app logic vector
mxScannDrives.unlock();
//printDrives(&vecDrives);
//TODO update UI
ui->updateTUI(&vecDrives);
ui->updateTUI(&vecDrives, i32SelectedEntry);
mxScannDrives.unlock();
}
else if (FD_ISSET(fdWhipe[0], &selectSet)) {
else if (FD_ISSET(fdWhipe[0], &selectSet))
{
cout << "Whipe signal" << endl;
//update percantage & state
//update ui
}
} //endless loop
thDevices.join();
thUserInput.join();
}
void reHDD::ThreadScannDevices() {
while(true) {
void reHDD::ThreadScannDevices()
{
while(true)
{
// cout << "Thread" << endl;
mxScannDrives.lock();
vecNewDrives.clear();
@ -94,18 +105,22 @@ void reHDD::ThreadScannDevices() {
}
}
void reHDD::ThreadUserInput() {
while(true) {
void reHDD::ThreadUserInput()
{
while(true)
{
// cout << TUI::readUserInput() << endl;
switch (TUI::readUserInput())
{
case TUI::UserInput::DownKey:
/* code */
//cout << "Down" << endl;
handleArrowKey(TUI::UserInput::DownKey);
ui->updateTUI(&vecDrives, i32SelectedEntry);
break;
case TUI::UserInput::UpKey:
//cout << "Up" << endl;
handleArrowKey(TUI::UserInput::UpKey);
ui->updateTUI(&vecDrives, i32SelectedEntry);
break;
case TUI::UserInput::Undefined:
//cout << "Undefined" << endl;
@ -131,7 +146,8 @@ void reHDD::ThreadUserInput() {
}
}
void reHDD::filterNewDrives(vector <Drive>* pvecOldDrives, vector <Drive>* pvecNewDrives) {
void reHDD::filterNewDrives(vector <Drive>* pvecOldDrives, vector <Drive>* pvecNewDrives)
{
vector <Drive>::iterator itOld; //Iterator for current (old) drive list
vector <Drive>::iterator itNew; //Iterator for new drive list that was created from to scann thread
@ -141,20 +157,23 @@ void reHDD::filterNewDrives(vector <Drive>* pvecOldDrives, vector <Drive>* pvecN
bool bOldDriveIsOffline = true;
for (itNew = pvecNewDrives->begin(); itNew != pvecNewDrives->end(); ++itNew)
{
if(itOld->getSerial() == itNew->getSerial()) {
if(itOld->getSerial() == itNew->getSerial())
{
bOldDriveIsOffline = false;
// cout << "already online drive found: " << itOld->getPath() << endl;
}
}
if(bOldDriveIsOffline == true) {
if(bOldDriveIsOffline == true)
{
//cout << "offline drive found: " << itOld->getPath() << endl;
//TODO kill wipe thread
}
}
pvecOldDrives->clear();
for (long unsigned int i=0; i<pvecNewDrives->size(); i++) {
for (long unsigned int i=0; i<pvecNewDrives->size(); i++)
{
pvecOldDrives->push_back((*pvecNewDrives)[i]);
}
}
@ -313,3 +332,28 @@ void reHDD::addSMARTData(vector <Drive>* pvecDrives)
SMART::readSMARTData(pTmpDrive);
}
}
void reHDD::handleArrowKey(TUI::UserInput userInput)
{
int32_t i32EntrySize = (int32_t) vecDrives.size();
switch (userInput)
{
case TUI::UserInput::DownKey:
i32SelectedEntry++;
if(i32SelectedEntry >= i32EntrySize)
{
i32SelectedEntry = 0;
}
break;
case TUI::UserInput::UpKey:
i32SelectedEntry--;
if(i32SelectedEntry < 0)
{
i32SelectedEntry = (i32EntrySize-1);
}
break;
default:
i32SelectedEntry = 0;
break;
}
}

View File

@ -64,7 +64,8 @@ void SMART::parseModelFamily(string sLine)
{
string search("\"model_family\": ");
size_t found = sLine.find(search);
if (found!=string::npos) {
if (found!=string::npos)
{
sLine.erase(0, sLine.find(": ") + 3);
sLine.erase(sLine.length()-3, 3);
modelFamily = sLine;
@ -80,7 +81,8 @@ void SMART::parseModelName(string sLine)
{
string search("\"model_name\": ");
size_t found = sLine.find(search);
if (found!=string::npos) {
if (found!=string::npos)
{
sLine.erase(0, sLine.find(": ") + 3);
sLine.erase(sLine.length()-3, 3);
modelName = sLine;
@ -96,7 +98,8 @@ void SMART::parseSerial(string sLine)
{
string search("\"serial_number\": ");
size_t found = sLine.find(search);
if (found!=string::npos) {
if (found!=string::npos)
{
sLine.erase(0, sLine.find(": ") + 3);
sLine.erase(sLine.length()-3, 3);
serial = sLine;
@ -112,7 +115,8 @@ void SMART::parseCapacity(string sLine)
{
string search("\"bytes\": ");
size_t found = sLine.find(search);
if (found!=string::npos) {
if (found!=string::npos)
{
sLine.erase(0, sLine.find(": ") + 2);
sLine.erase(sLine.length()-1, 1);
capacity = stol(sLine);