annotate data/model/PowerOfSqrtTwoZoomConstraint.cpp @ 1528:a7485c1bdba5

Tests and a couple of minor fixes for zoom constraints
author Chris Cannam
date Tue, 18 Sep 2018 15:04:46 +0100
parents 48e9f538e6e9
children c1c45c5146bb
rev   line source
Chris@147 1 /* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */
Chris@147 2
Chris@147 3 /*
Chris@147 4 Sonic Visualiser
Chris@147 5 An audio file viewer and annotation editor.
Chris@147 6 Centre for Digital Music, Queen Mary, University of London.
Chris@147 7 This file copyright 2006 Chris Cannam.
Chris@147 8
Chris@147 9 This program is free software; you can redistribute it and/or
Chris@147 10 modify it under the terms of the GNU General Public License as
Chris@147 11 published by the Free Software Foundation; either version 2 of the
Chris@147 12 License, or (at your option) any later version. See the file
Chris@147 13 COPYING included with this distribution for more information.
Chris@147 14 */
Chris@147 15
Chris@147 16 #include "PowerOfSqrtTwoZoomConstraint.h"
Chris@147 17
Chris@147 18 #include <iostream>
Chris@147 19 #include <cmath>
Chris@147 20
Chris@1528 21 #include "base/Debug.h"
Chris@1528 22
Chris@147 23
Chris@929 24 int
Chris@929 25 PowerOfSqrtTwoZoomConstraint::getNearestBlockSize(int blockSize,
Chris@1429 26 RoundingDirection dir) const
Chris@147 27 {
Chris@147 28 int type, power;
Chris@929 29 int rv = getNearestBlockSize(blockSize, type, power, dir);
Chris@147 30 return rv;
Chris@147 31 }
Chris@147 32
Chris@929 33 int
Chris@929 34 PowerOfSqrtTwoZoomConstraint::getNearestBlockSize(int blockSize,
Chris@1429 35 int &type,
Chris@1429 36 int &power,
Chris@1429 37 RoundingDirection dir) const
Chris@147 38 {
Chris@1528 39 // SVCERR << "given " << blockSize << endl;
Chris@147 40
Chris@929 41 int minCachePower = getMinCachePower();
Chris@147 42
Chris@929 43 if (blockSize < (1 << minCachePower)) {
Chris@1429 44 type = -1;
Chris@1429 45 power = 0;
Chris@1429 46 float val = 1.0, prevVal = 1.0;
Chris@1429 47 while (val + 0.01 < blockSize) {
Chris@1429 48 prevVal = val;
Chris@1429 49 val *= sqrtf(2.f);
Chris@1429 50 }
Chris@1528 51 int rval = int(val + 0.01f);
Chris@1528 52 // SVCERR << "got val = " << val << ", rval = " << rval << ", prevVal = " << prevVal << endl;
Chris@1528 53 if (rval != blockSize && dir != RoundUp) {
Chris@1528 54 if (dir == RoundDown) {
Chris@1528 55 rval = int(prevVal + 0.01f);
Chris@1528 56 } else if (val - float(blockSize) < float(blockSize) - prevVal) {
Chris@1528 57 rval = int(val + 0.01f);
Chris@1528 58 } else {
Chris@1528 59 rval = int(prevVal + 0.01);
Chris@1528 60 }
Chris@1528 61 }
Chris@1528 62 // SVCERR << "returning " << rval << endl;
Chris@1429 63 return rval;
Chris@147 64 }
Chris@147 65
Chris@929 66 int prevBase = (1 << minCachePower);
Chris@929 67 int prevPower = minCachePower;
Chris@929 68 int prevType = 0;
Chris@147 69
Chris@929 70 int result = 0;
Chris@147 71
Chris@147 72 for (unsigned int i = 0; ; ++i) {
Chris@147 73
Chris@1429 74 power = minCachePower + i/2;
Chris@1429 75 type = i % 2;
Chris@147 76
Chris@1429 77 int base;
Chris@1429 78 if (type == 0) {
Chris@1429 79 base = (1 << power);
Chris@1429 80 } else {
Chris@1429 81 base = (((unsigned int)((1 << minCachePower) * sqrt(2.) + 0.01))
Chris@1429 82 << (power - minCachePower));
Chris@1429 83 }
Chris@147 84
Chris@1528 85 // SVCERR << "Testing base " << base << " (i = " << i << ", power = " << power << ", type = " << type << ")" << endl;
Chris@377 86
Chris@377 87 if (base == blockSize) {
Chris@377 88 result = base;
Chris@377 89 break;
Chris@377 90 }
Chris@377 91
Chris@1429 92 if (base > blockSize) {
Chris@1429 93 if (dir == RoundNearest) {
Chris@1429 94 if (base - blockSize < blockSize - prevBase) {
Chris@1429 95 dir = RoundUp;
Chris@1429 96 } else {
Chris@1429 97 dir = RoundDown;
Chris@1429 98 }
Chris@1429 99 }
Chris@1429 100 if (dir == RoundUp) {
Chris@1429 101 result = base;
Chris@1429 102 break;
Chris@1429 103 } else {
Chris@1429 104 type = prevType;
Chris@1429 105 power = prevPower;
Chris@1429 106 result = prevBase;
Chris@1429 107 break;
Chris@1429 108 }
Chris@1429 109 }
Chris@147 110
Chris@1429 111 prevType = type;
Chris@1429 112 prevPower = power;
Chris@1429 113 prevBase = base;
Chris@147 114 }
Chris@147 115
Chris@147 116 if (result > getMaxZoomLevel()) result = getMaxZoomLevel();
Chris@147 117 return result;
Chris@147 118 }