Refine date header visibility logic and scroll behavior in GetLastTransactionsScript:
- Add `computeDateYCount` to detect overlapping date headers and improve visibility checks. - Adjust swipe logic for better handling of target and older dates during transaction fetching. -
This commit is contained in:
parent
779e3cd74c
commit
bac36aa5d2
@ -277,17 +277,36 @@ void GetLastTransactionsScript::searchTransaction(const DeviceInfo &device, int
|
|||||||
return QDate(searchDate.year(), month, day);
|
return QDate(searchDate.year(), month, day);
|
||||||
};
|
};
|
||||||
|
|
||||||
auto hasDateOnScreen = [&]() -> bool {
|
// Ozon WebView сворачивает заголовки дат вне вьюпорта в один y (0 или общий
|
||||||
|
// верхний y). Несколько разных дат на одной y-позиции — pile-up скрытых
|
||||||
|
// заголовков, их надо считать невидимыми.
|
||||||
|
auto computeDateYCount = [&]() -> QMap<int, int> {
|
||||||
|
QMap<int, int> cnt;
|
||||||
for (const Node &node : xmlScreenParser.getNodes()) {
|
for (const Node &node : xmlScreenParser.getNodes()) {
|
||||||
if (node.className != "android.widget.TextView") continue;
|
if (node.className != "android.widget.TextView") continue;
|
||||||
|
if (node.y() <= 0) continue;
|
||||||
|
if (parseDateHeader(node.text.trimmed()).isValid()) cnt[node.y()]++;
|
||||||
|
}
|
||||||
|
return cnt;
|
||||||
|
};
|
||||||
|
|
||||||
|
auto hasDateOnScreen = [&]() -> bool {
|
||||||
|
const QMap<int, int> yCount = computeDateYCount();
|
||||||
|
for (const Node &node : xmlScreenParser.getNodes()) {
|
||||||
|
if (node.className != "android.widget.TextView") continue;
|
||||||
|
if (node.y() <= 0) continue;
|
||||||
|
if (yCount.value(node.y(), 0) != 1) continue;
|
||||||
if (parseDateHeader(node.text.trimmed()) == searchDate) return true;
|
if (parseDateHeader(node.text.trimmed()) == searchDate) return true;
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
};
|
};
|
||||||
|
|
||||||
auto hasOlderDateOnScreen = [&]() -> bool {
|
auto hasOlderDateOnScreen = [&]() -> bool {
|
||||||
|
const QMap<int, int> yCount = computeDateYCount();
|
||||||
for (const Node &node : xmlScreenParser.getNodes()) {
|
for (const Node &node : xmlScreenParser.getNodes()) {
|
||||||
if (node.className != "android.widget.TextView") continue;
|
if (node.className != "android.widget.TextView") continue;
|
||||||
|
if (node.y() <= 0) continue;
|
||||||
|
if (yCount.value(node.y(), 0) != 1) continue;
|
||||||
const QDate d = parseDateHeader(node.text.trimmed());
|
const QDate d = parseDateHeader(node.text.trimmed());
|
||||||
if (d.isValid() && d < searchDate) return true;
|
if (d.isValid() && d < searchDate) return true;
|
||||||
}
|
}
|
||||||
@ -345,6 +364,9 @@ void GetLastTransactionsScript::searchTransaction(const DeviceInfo &device, int
|
|||||||
// видна ниже (или не видна вовсе), dateY = 0 — все кнопки выше nextDateY
|
// видна ниже (или не видна вовсе), dateY = 0 — все кнопки выше nextDateY
|
||||||
// принадлежат нашему дню.
|
// принадлежат нашему дню.
|
||||||
auto findDateYRange = [&]() -> QPair<int, int> {
|
auto findDateYRange = [&]() -> QPair<int, int> {
|
||||||
|
const QMap<int, int> yCount = computeDateYCount();
|
||||||
|
auto isVisible = [&](int y) { return y > 0 && yCount.value(y, 0) == 1; };
|
||||||
|
|
||||||
int dateY = -1;
|
int dateY = -1;
|
||||||
int nextDateY = device.screenHeight;
|
int nextDateY = device.screenHeight;
|
||||||
bool foundOlderDate = false;
|
bool foundOlderDate = false;
|
||||||
@ -353,23 +375,18 @@ void GetLastTransactionsScript::searchTransaction(const DeviceInfo &device, int
|
|||||||
const QDate d = parseDateHeader(node.text.trimmed());
|
const QDate d = parseDateHeader(node.text.trimmed());
|
||||||
if (!d.isValid()) continue;
|
if (!d.isValid()) continue;
|
||||||
if (d == searchDate) {
|
if (d == searchDate) {
|
||||||
dateY = node.y();
|
if (isVisible(node.y())) dateY = node.y();
|
||||||
} else if (d < searchDate) {
|
} else if (d < searchDate) {
|
||||||
// Заголовок более старой даты — граница снизу
|
|
||||||
if (dateY >= 0 && node.y() > dateY) {
|
|
||||||
nextDateY = node.y();
|
|
||||||
} else if (dateY < 0) {
|
|
||||||
// Заголовок нужной даты ушёл вверх, но видна более старая дата
|
|
||||||
nextDateY = node.y();
|
|
||||||
dateY = 0; // всё выше nextDateY принадлежит нашему дню
|
|
||||||
}
|
|
||||||
foundOlderDate = true;
|
foundOlderDate = true;
|
||||||
break;
|
if (isVisible(node.y()) && (dateY < 0 || node.y() > dateY)
|
||||||
|
&& node.y() < nextDateY) {
|
||||||
|
nextDateY = node.y();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// Заголовок ушёл вверх и нет более старых дат на экране —
|
// Target-header не виден, но видна более старая дата → target ушёл вверх:
|
||||||
// весь экран всё ещё внутри нашей даты
|
// всё выше nextDateY принадлежит нашему дню.
|
||||||
if (dateY < 0 && !foundOlderDate && dateFound) {
|
if (dateY < 0 && nextDateY < device.screenHeight) {
|
||||||
dateY = 0;
|
dateY = 0;
|
||||||
}
|
}
|
||||||
qDebug() << "[FetchTransactions] findDateYRange: dateY=" << dateY
|
qDebug() << "[FetchTransactions] findDateYRange: dateY=" << dateY
|
||||||
@ -405,11 +422,13 @@ void GetLastTransactionsScript::searchTransaction(const DeviceInfo &device, int
|
|||||||
// Находим Y-диапазон заголовка нужной даты
|
// Находим Y-диапазон заголовка нужной даты
|
||||||
const auto [dateHeaderY, nextDateHeaderY] = findDateYRange();
|
const auto [dateHeaderY, nextDateHeaderY] = findDateYRange();
|
||||||
if (dateHeaderY < 0) {
|
if (dateHeaderY < 0) {
|
||||||
qDebug() << "[FetchTransactions] Date completely off screen, scrolling up";
|
// Target-header не виден и ни одной более старой даты не видно →
|
||||||
|
// target скорее всего ниже вьюпорта. Скроллим вниз (swipe вверх).
|
||||||
|
qDebug() << "[FetchTransactions] Target not visible, no older date — scrolling down";
|
||||||
AdbUtils::makeSwipe(m_deviceId, device.screenWidth / 2,
|
AdbUtils::makeSwipe(m_deviceId, device.screenWidth / 2,
|
||||||
device.screenHeight / 3,
|
device.screenHeight * 2 / 3,
|
||||||
device.screenWidth / 2,
|
device.screenWidth / 2,
|
||||||
device.screenHeight * 2 / 3, 600);
|
device.screenHeight / 3, 500);
|
||||||
QThread::msleep(1500);
|
QThread::msleep(1500);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
@ -641,23 +660,33 @@ void GetLastTransactionsScript::searchTransaction(const DeviceInfo &device, int
|
|||||||
noProgressCount = 0;
|
noProgressCount = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Скроллим вниз если не нашли нужную транзакцию
|
// Скроллим если не нашли нужную транзакцию
|
||||||
if (!tapped || !hasNewButton) {
|
if (!tapped || !hasNewButton) {
|
||||||
qDebug() << "[FetchTransactions] Scrolling down (tapped=" << tapped
|
qDebug() << "[FetchTransactions] Scrolling (tapped=" << tapped
|
||||||
<< "hasNew=" << hasNewButton << "inRange=" << buttonsInRange
|
<< "hasNew=" << hasNewButton << "inRange=" << buttonsInRange
|
||||||
<< "noProgress=" << noProgressCount << ")";
|
<< "noProgress=" << noProgressCount
|
||||||
|
<< "dateHeaderY=" << dateHeaderY
|
||||||
|
<< "nextDateHeaderY=" << nextDateHeaderY << ")";
|
||||||
|
|
||||||
if (dateHeaderY > 0 && dateHeaderY < device.screenHeight / 2) {
|
if (dateHeaderY == 0 && nextDateHeaderY < device.screenHeight) {
|
||||||
|
// Target-header ушёл вверх, под ним видна более старая дата —
|
||||||
|
// скроллим обратно наверх (swipe вниз) чтобы вернуться к target.
|
||||||
|
const int fromY = device.screenHeight / 3;
|
||||||
|
const int toY = device.screenHeight * 2 / 3;
|
||||||
|
qDebug() << "[FetchTransactions] Scroll UP: from" << fromY << "to" << toY;
|
||||||
|
AdbUtils::makeSwipe(m_deviceId, device.screenWidth / 2, fromY,
|
||||||
|
device.screenWidth / 2, toY, 500);
|
||||||
|
} else if (dateHeaderY > 0 && dateHeaderY < device.screenHeight / 2) {
|
||||||
// Заголовок в верхней половине — маленький скролл чтобы показать
|
// Заголовок в верхней половине — маленький скролл чтобы показать
|
||||||
// больше кнопок под этой датой
|
// больше кнопок под этой датой
|
||||||
const int fromY = device.screenHeight * 2 / 3;
|
const int fromY = device.screenHeight * 2 / 3;
|
||||||
const int toY = device.screenHeight / 3;
|
const int toY = device.screenHeight / 3;
|
||||||
qDebug() << "[FetchTransactions] Small scroll: from" << fromY << "to" << toY
|
qDebug() << "[FetchTransactions] Small scroll down: from" << fromY << "to" << toY
|
||||||
<< "(dateHeaderY=" << dateHeaderY << ")";
|
<< "(dateHeaderY=" << dateHeaderY << ")";
|
||||||
AdbUtils::makeSwipe(m_deviceId, device.screenWidth / 2, fromY,
|
AdbUtils::makeSwipe(m_deviceId, device.screenWidth / 2, fromY,
|
||||||
device.screenWidth / 2, toY, 500);
|
device.screenWidth / 2, toY, 500);
|
||||||
} else {
|
} else {
|
||||||
// Заголовок в нижней половине или за экраном — полный скролл
|
// Заголовок в нижней половине или не найден — скролл вниз
|
||||||
const int fromY = device.screenHeight * 3 / 4;
|
const int fromY = device.screenHeight * 3 / 4;
|
||||||
const int toY = device.screenHeight / 4;
|
const int toY = device.screenHeight / 4;
|
||||||
qDebug() << "[FetchTransactions] Full scroll down: from" << fromY << "to" << toY
|
qDebug() << "[FetchTransactions] Full scroll down: from" << fromY << "to" << toY
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user