move common code into PackageManager::StatusChanged()
[ntk/apt.git] / apt-pkg / iprogress.cc
CommitLineData
31f97d7b
MV
1#include <apt-pkg/iprogress.h>
2#include <apt-pkg/strutl.h>
6c5ae8ed 3#include <apti18n.h>
31f97d7b
MV
4
5#include <termios.h>
6#include <sys/ioctl.h>
7
8namespace APT {
9namespace Progress {
10
6c5ae8ed
MV
11bool PackageManager::StatusChanged(std::string PackageName,
12 unsigned int StepsDone,
13 unsigned int TotalSteps)
14{
15 int reporting_steps = _config->FindI("DpkgPM::Reporting-Steps", 1);
16 percentage = StepsDone/(float)TotalSteps * 100.0;
17 strprintf(progress_str, _("Progress: [%3i%%]"), (int)percentage);
18
19 if(percentage < (last_reported_progress + reporting_steps))
20 return false;
21
22 return true;
23}
24
db78c60c 25void PackageManagerFancy::SetupTerminalScrollArea(int nr_rows)
31f97d7b
MV
26{
27 // scroll down a bit to avoid visual glitch when the screen
28 // area shrinks by one row
29 std::cout << "\n";
30
31 // save cursor
32 std::cout << "\033[s";
33
34 // set scroll region (this will place the cursor in the top left)
35 std::cout << "\033[1;" << nr_rows - 1 << "r";
36
37 // restore cursor but ensure its inside the scrolling area
38 std::cout << "\033[u";
39 static const char *move_cursor_up = "\033[1A";
40 std::cout << move_cursor_up;
db78c60c 41
31f97d7b
MV
42 std::flush(std::cout);
43}
44
45PackageManagerFancy::PackageManagerFancy()
46 : nr_terminal_rows(-1)
47{
48 struct winsize win;
49 if(ioctl(STDOUT_FILENO, TIOCGWINSZ, (char *)&win) == 0)
50 {
51 nr_terminal_rows = win.ws_row;
52 }
53}
54
55void PackageManagerFancy::Started()
56{
db78c60c
MV
57 if (nr_terminal_rows > 0)
58 SetupTerminalScrollArea(nr_terminal_rows);
31f97d7b
MV
59}
60
61void PackageManagerFancy::Finished()
62{
db78c60c
MV
63 if (nr_terminal_rows > 0)
64 {
65 SetupTerminalScrollArea(nr_terminal_rows + 1);
31f97d7b 66
db78c60c
MV
67 // override the progress line (sledgehammer)
68 static const char* clear_screen_below_cursor = "\033[J";
69 std::cout << clear_screen_below_cursor;
70 }
31f97d7b
MV
71}
72
6c5ae8ed 73bool PackageManagerFancy::StatusChanged(std::string PackageName,
31f97d7b
MV
74 unsigned int StepsDone,
75 unsigned int TotalSteps)
76{
6c5ae8ed
MV
77 if (!PackageManager::StatusChanged(PackageName, StepsDone, TotalSteps))
78 return false;
31f97d7b
MV
79
80 int row = nr_terminal_rows;
81
82 static string save_cursor = "\033[s";
83 static string restore_cursor = "\033[u";
84
85 static string set_bg_color = "\033[42m"; // green
86 static string set_fg_color = "\033[30m"; // black
87
88 static string restore_bg = "\033[49m";
89 static string restore_fg = "\033[39m";
90
91 std::cout << save_cursor
92 // move cursor position to last row
93 << "\033[" << row << ";0f"
94 << set_bg_color
95 << set_fg_color
96 << progress_str
97 << restore_cursor
98 << restore_bg
99 << restore_fg;
100 std::flush(std::cout);
101 last_reported_progress = percentage;
6c5ae8ed
MV
102
103 return true;
31f97d7b
MV
104}
105
6c5ae8ed 106bool PackageManagerText::StatusChanged(std::string PackageName,
31f97d7b
MV
107 unsigned int StepsDone,
108 unsigned int TotalSteps)
109{
6c5ae8ed
MV
110 if (!PackageManager::StatusChanged(PackageName, StepsDone, TotalSteps))
111 return false;
31f97d7b
MV
112
113 std::cout << progress_str << "\r\n";
114 std::flush(std::cout);
115
116 last_reported_progress = percentage;
6c5ae8ed
MV
117
118 return true;
31f97d7b
MV
119}
120
121
122}; // namespace progress
123}; // namespace apt