diff --git a/mythtv/libs/libmythtv/subtitlescreen.cpp b/mythtv/libs/libmythtv/subtitlescreen.cpp
index 1290bff..62fdf1c 100644
a
|
b
|
SubtitleFormat::GetFont(const QString &family, |
335 | 335 | result->SetOutline(outline, color, off, alpha); |
336 | 336 | |
337 | 337 | LOG(VB_VBI, LOG_DEBUG, |
338 | | QString("GetFont(family=%1, prefix=%2, orig pixelSize=%3, " |
339 | | "new pixelSize=%4 zoom=%5) = %6") |
340 | | .arg(family).arg(prefix).arg(origPixelSize).arg(pixelSize) |
341 | | .arg(zoom).arg(fontToString(result))); |
| 338 | QString("GetFont(family=%1 prefix=%2 orig pixelSize=%3 zoom=%4 stretch=%5) = %6") |
| 339 | .arg(family).arg(prefix).arg(origPixelSize) |
| 340 | .arg(zoom).arg(stretch).arg(fontToString(result))); |
342 | 341 | return result; |
343 | 342 | } |
344 | 343 | |
… |
… |
bool FormattedTextChunk::PreRender(bool isFirst, bool isLast, |
690 | 689 | int leftPadding, rightPadding; |
691 | 690 | CalcPadding(isFirst, isLast, leftPadding, rightPadding); |
692 | 691 | // Account for extra padding before the first chunk. |
693 | | if (isFirst) |
694 | | x += leftPadding; |
| 692 | // No, this will cause everything to be off center to the right |
| 693 | // by the value of leftPadding. |
| 694 | // if (isFirst) |
| 695 | // x += leftPadding; |
695 | 696 | QSize chunk_sz = CalcSize(); |
696 | 697 | QRect bgrect(x - leftPadding, y, |
697 | 698 | chunk_sz.width() + leftPadding + rightPadding, |
… |
… |
void FormattedTextSubtitle::Draw(void) |
909 | 910 | // order of the children. In particular, background |
910 | 911 | // shapes should be added/drawn first, and text drawn on |
911 | 912 | // top. |
| 913 | LOG(VB_VBI, LOG_DEBUG, |
| 914 | QString("i=%1 rect=%2x%3@%4,%5 bgrect=%6x%7@%8,%9 text=%10") |
| 915 | .arg(i) |
| 916 | .arg(chunk->textRect.width()) |
| 917 | .arg(chunk->textRect.height()) |
| 918 | .arg(chunk->textRect.x()) |
| 919 | .arg(chunk->textRect.y()) |
| 920 | .arg(chunk->bgShapeRect.width()) |
| 921 | .arg(chunk->bgShapeRect.height()) |
| 922 | .arg(chunk->bgShapeRect.x()) |
| 923 | .arg(chunk->bgShapeRect.y()) |
| 924 | .arg(chunk->text)); |
912 | 925 | SubSimpleText *text = |
913 | 926 | new SubSimpleText((*chunk).text, *mythfont, |
914 | 927 | (*chunk).textRect, |
… |
… |
void FormattedTextSubtitle608::Layout(void) |
1233 | 1246 | m_lines[i].y_indent = prevY + spaceBefore[i] * shrink; |
1234 | 1247 | prevY = m_lines[i].y_indent + heights[i]; |
1235 | 1248 | } |
| 1249 | LOG(VB_VBI, LOG_DEBUG, |
| 1250 | QString("Shrink overage=%1 totalSpace=%2 shrink=%3 firstY=%4 prevY=%5") |
| 1251 | .arg(overage).arg(totalSpace).arg(shrink).arg(firstY).arg(prevY)); |
1236 | 1252 | } |
1237 | 1253 | |
1238 | 1254 | // Shift Y coordinates back up into the safe area. |
… |
… |
void FormattedTextSubtitle608::Init(const vector<CC608Text*> &buffers) |
1254 | 1270 | if (buffers.empty()) |
1255 | 1271 | return; |
1256 | 1272 | vector<CC608Text*>::const_iterator i = buffers.begin(); |
1257 | | int xscale = 36; |
1258 | | int yscale = 17; |
1259 | | int pixelSize = m_safeArea.height() / (yscale * LINE_SPACING); |
| 1273 | |
| 1274 | int xscale = 32; // 608 max columns |
| 1275 | int yscale = 15; // 608 max rows |
| 1276 | |
| 1277 | // Set pixelSize to the target lineHeight |
| 1278 | // It is a first guess pixelSize, which will almost certainly be off |
| 1279 | int pixelSize = m_safeArea.height() / yscale; |
| 1280 | int lineHeight = pixelSize; |
1260 | 1281 | int fontwidth = 0; |
1261 | 1282 | int xmid = 0; |
1262 | 1283 | int zoom = 100; |
… |
… |
void FormattedTextSubtitle608::Init(const vector<CC608Text*> &buffers) |
1266 | 1287 | m_subScreen->SetFontSize(pixelSize); |
1267 | 1288 | CC708CharacterAttribute def_attr(false, false, false, clr[0]); |
1268 | 1289 | QFont *font = m_subScreen->GetFont(def_attr)->GetFace(); |
| 1290 | |
| 1291 | // Set the pixelSize, again, to undo scaling done by |
| 1292 | // SubtitleScreen::GetFont(). |
| 1293 | // It will be scaled appropriately after we establish |
| 1294 | // a baseline pixelSize for 100% zoom. |
| 1295 | font->setPixelSize(pixelSize); |
| 1296 | |
1269 | 1297 | QFontMetrics fm(*font); |
| 1298 | // Font metrics for various fonts are inconsistent in how |
| 1299 | // they provide a realistic line height value. |
| 1300 | // The max of what they call height and lineSpacing |
| 1301 | // provides a resonable value for most fonts. |
| 1302 | lineHeight = max(fm.height(), fm.lineSpacing()); |
| 1303 | |
| 1304 | int offBy = lineHeight - pixelSize; |
| 1305 | int newPixelSize = pixelSize; |
| 1306 | int newLineHeight = lineHeight; |
| 1307 | if (offBy != 0) |
| 1308 | { |
| 1309 | // We tried a pixelSize equal to the desired font height, |
| 1310 | // but it didn't quite get us there. |
| 1311 | // We make a better guess by applying a ratio of |
| 1312 | // our first guess divided by the actual height. |
| 1313 | // This should be "good enough" for most fonts. |
| 1314 | newPixelSize = pixelSize * pixelSize / lineHeight; |
| 1315 | m_subScreen->SetFontSize(newPixelSize); |
| 1316 | font = m_subScreen->GetFont(def_attr)->GetFace(); |
| 1317 | font->setPixelSize(newPixelSize); |
| 1318 | fm = QFontMetrics(*font); |
| 1319 | newLineHeight = max(fm.height(), fm.lineSpacing()); |
| 1320 | } |
1270 | 1321 | fontwidth = fm.averageCharWidth(); |
| 1322 | LOG(VB_VBI, LOG_DEBUG, |
| 1323 | QString("Unscaled pixelSize=%1->%2 lineHeight=%3->%4 fontwidth=%5 offBy=%6 zoom=%7") |
| 1324 | .arg(pixelSize).arg(newPixelSize).arg(lineHeight).arg(newLineHeight) |
| 1325 | .arg(fontwidth).arg(offBy).arg(zoom)); |
| 1326 | lineHeight = newLineHeight; |
| 1327 | |
| 1328 | // Now that we have our baseline, |
| 1329 | // we can apply the zoom factor. |
| 1330 | if (zoom != 100) |
| 1331 | { |
| 1332 | font = m_subScreen->GetFont(def_attr)->GetFace(); |
| 1333 | fm = QFontMetrics(*font); |
| 1334 | fontwidth = fm.averageCharWidth(); |
| 1335 | lineHeight = max(fm.height(), fm.lineSpacing()); |
| 1336 | LOG(VB_VBI, LOG_DEBUG, |
| 1337 | QString("Scaled lineHeight=%1 fontwidth=%2") |
| 1338 | .arg(lineHeight).arg(fontwidth)); |
| 1339 | } |
1271 | 1340 | xmid = m_safeArea.width() / 2; |
1272 | 1341 | // Disable centering for zoom factor >= 100% |
1273 | | if (zoom >= 100) |
1274 | | xscale = m_safeArea.width() / fontwidth; |
| 1342 | // Why?? If disabled, 608 captions are shifted to left unless |
| 1343 | // the user sets the zoom to 99% or less. |
| 1344 | // The Layout method should shift left-right and up-down |
| 1345 | // as needed for zoom factor. |
| 1346 | // If zoom factor is too large, the user can reduce it. |
| 1347 | //if (zoom >= 100) |
| 1348 | // xscale = m_safeArea.width() / fontwidth; |
1275 | 1349 | } |
1276 | 1350 | |
1277 | 1351 | for (; i != buffers.end(); ++i) |
… |
… |
void FormattedTextSubtitle608::Init(const vector<CC608Text*> &buffers) |
1282 | 1356 | const bool isBold = false; |
1283 | 1357 | QString text(cc->text); |
1284 | 1358 | |
| 1359 | // Note: cc-x (and orig_x) is column # ranging from 0 through 31, |
1285 | 1360 | int orig_x = cc->x; |
1286 | 1361 | // position as if we use a fixed size font |
1287 | 1362 | // - font size already has zoom factor applied |
… |
… |
void FormattedTextSubtitle608::Init(const vector<CC608Text*> &buffers) |
1294 | 1369 | // fallback |
1295 | 1370 | x = (orig_x + 3) * m_safeArea.width() / xscale; |
1296 | 1371 | |
| 1372 | // Note: cc-y (and orig_y) is row # ranging from 1 through 15, |
| 1373 | // we need zero based rows |
1297 | 1374 | int orig_y = cc->y; |
1298 | 1375 | int y; |
1299 | | if (orig_y < yscale / 2) |
| 1376 | if (orig_y <= yscale / 2) |
1300 | 1377 | // top half -- anchor up |
1301 | | y = (orig_y * m_safeArea.height() * zoom / (yscale * 100)); |
| 1378 | y = (orig_y-1) * lineHeight; |
1302 | 1379 | else |
1303 | 1380 | // bottom half -- anchor down |
1304 | | y = m_safeArea.height() - |
1305 | | ((yscale - orig_y - 0.5) * m_safeArea.height() * zoom / |
1306 | | (yscale * 100)); |
| 1381 | y = m_safeArea.height() - ((yscale - (orig_y-1)) * lineHeight); |
1307 | 1382 | |
1308 | 1383 | FormattedTextLine line(x, y, orig_x, orig_y); |
1309 | 1384 | while (!text.isNull()) |
… |
… |
QSize SubtitleScreen::CalcTextSize(const QString &text, |
1661 | 1736 | QFont *font = mythfont->GetFace(); |
1662 | 1737 | QFontMetrics fm(*font); |
1663 | 1738 | int width = fm.width(text); |
1664 | | int height = fm.height() * (1 + PAD_HEIGHT); |
| 1739 | |
| 1740 | // Font metrics for various fonts are inconsistent in how |
| 1741 | // they provide a realistic line height value. |
| 1742 | // The max of what they call height and lineSpacing |
| 1743 | // provides a resonable value for most fonts. |
| 1744 | int height = max(fm.height(), fm.lineSpacing()); |
| 1745 | |
1665 | 1746 | if (layoutSpacing > 0 && !text.trimmed().isEmpty()) |
1666 | 1747 | height = max(height, (int)(font->pixelSize() * layoutSpacing)); |
1667 | 1748 | height += CalcShadowOffsetPadding(mythfont).height(); |
… |
… |
void SubtitleScreen::OptimiseDisplayedArea(void) |
1813 | 1894 | return; |
1814 | 1895 | |
1815 | 1896 | QRect bounding = visible.boundingRect(); |
| 1897 | LOG(VB_VBI, LOG_DEBUG, |
| 1898 | QString("Visible bounds=%1x%2@%3,%4") |
| 1899 | .arg(bounding.width()).arg(bounding.height()) |
| 1900 | .arg(bounding.x()).arg(bounding.y())); |
| 1901 | |
1816 | 1902 | bounding = bounding.translated(m_safeArea.topLeft()); |
| 1903 | LOG(VB_VBI, LOG_DEBUG, |
| 1904 | QString("Translated bounds=%1x%2@%3,%4") |
| 1905 | .arg(bounding.width()).arg(bounding.height()) |
| 1906 | .arg(bounding.x()).arg(bounding.y())); |
| 1907 | |
1817 | 1908 | bounding = m_safeArea.intersected(bounding); |
1818 | 1909 | int left = m_safeArea.left() - bounding.left(); |
1819 | 1910 | int top = m_safeArea.top() - bounding.top(); |
| 1911 | LOG(VB_VBI, LOG_DEBUG, |
| 1912 | QString("Intersected bounds=%1x%2@%3,%4 left=%5 right=%6") |
| 1913 | .arg(bounding.width()).arg(bounding.height()) |
| 1914 | .arg(bounding.x()).arg(bounding.y()) |
| 1915 | .arg(left).arg(top)); |
1820 | 1916 | SetArea(MythRect(bounding)); |
1821 | 1917 | |
1822 | 1918 | i.toFront(); |