Changeset 206445 in webkit
- Timestamp:
- Sep 27, 2016, 10:58:44 AM (9 years ago)
- Location:
- trunk/Source/WebCore
- Files:
-
- 14 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/WebCore/ChangeLog
r206444 r206445 1 2016-09-27 Eric Carlson <eric.carlson@apple.com> 2 3 [MediaStream] Restructure MediaConstraints classes 4 https://bugs.webkit.org/show_bug.cgi?id=162571 5 6 Reviewed by Jer Noble. 7 8 No new tests, no functional changes. 9 10 * Modules/mediastream/MediaConstraintsImpl.cpp: 11 (WebCore::MediaConstraintsImpl::initialize): Deleted, no longer used. 12 * Modules/mediastream/MediaConstraintsImpl.h: 13 14 * bindings/js/JSMediaDevicesCustom.cpp: 15 (WebCore::createStringConstraint): Return Optional<> instead of RefPtr<>. 16 (WebCore::createBooleanConstraint): Ditto. 17 (WebCore::createDoubleConstraint): Ditto. 18 (WebCore::createIntConstraint): Ditto. 19 (WebCore::parseMediaTrackConstraintSetForKey): Deal with above change. 20 21 * platform/mediastream/CaptureDeviceManager.cpp: 22 (CaptureDeviceManager::verifyConstraintsForMediaType): Use constraints.mandatoryConstraints.filter 23 instead of direct enumeration. 24 (CaptureDeviceManager::sessionSupportsConstraint): Use downcast<>. 25 (CaptureDeviceManager::isSupportedFrameRate): Ditto. 26 27 * platform/mediastream/MediaConstraints.cpp: 28 (WebCore::StringConstraint::find): Lose the ConstraintType parameter. 29 (WebCore::StringConstraint::merge): Use downcast<>. 30 (WebCore::FlattenedConstraint::set): Use ConstraintHolder. 31 (WebCore::FlattenedConstraint::merge): Ditto. 32 (WebCore::MediaTrackConstraintSetMap::forEach): New. 33 (WebCore::MediaTrackConstraintSetMap::filter): Ditto. 34 (WebCore::MediaTrackConstraintSetMap::isEmpty): Ditto. 35 (WebCore::MediaTrackConstraintSetMap::set): Ditto. 36 (WebCore::MediaConstraint::copy): Deleted. 37 (WebCore::IntConstraint::copy): Deleted. 38 (WebCore::DoubleConstraint::copy): Deleted. 39 (WebCore::BooleanConstraint::copy): Deleted. 40 (WebCore::StringConstraint::copy): Deleted. 41 * platform/mediastream/MediaConstraints.h: 42 (WebCore::MediaConstraint::MediaConstraint): 43 (WebCore::MediaConstraint::isEmpty): 44 (WebCore::MediaConstraint::isMandatory): 45 (WebCore::MediaConstraint::merge): 46 (WebCore::MediaConstraint::isInt): 47 (WebCore::MediaConstraint::isDouble): 48 (WebCore::MediaConstraint::isBoolean): 49 (WebCore::MediaConstraint::isString): 50 (WebCore::MediaConstraint::dataType): 51 (WebCore::MediaConstraint::constraintType): 52 (WebCore::NumericConstraint::getMin): 53 (WebCore::NumericConstraint::getMax): 54 (WebCore::NumericConstraint::getExact): 55 (WebCore::NumericConstraint::getIdeal): 56 (WebCore::NumericConstraint::fitnessDistance): 57 (WebCore::NumericConstraint::validForRange): 58 (WebCore::NumericConstraint::find): 59 (WebCore::NumericConstraint::NumericConstraint): 60 (WebCore::NumericConstraint::innerMerge): 61 (WebCore::FlattenedConstraint::isEmpty): 62 (WebCore::FlattenedConstraint::iterator::iterator): 63 (WebCore::FlattenedConstraint::iterator::operator*): 64 (WebCore::FlattenedConstraint::iterator::operator++): 65 (WebCore::FlattenedConstraint::iterator::operator==): 66 (WebCore::FlattenedConstraint::iterator::operator!=): 67 (WebCore::FlattenedConstraint::begin): 68 (WebCore::FlattenedConstraint::end): 69 (WebCore::FlattenedConstraint::ConstraintHolder::create): 70 (WebCore::FlattenedConstraint::ConstraintHolder::~ConstraintHolder): 71 (WebCore::FlattenedConstraint::ConstraintHolder::constraint): 72 (WebCore::FlattenedConstraint::ConstraintHolder::dataType): 73 (WebCore::FlattenedConstraint::ConstraintHolder::constraintType): 74 (WebCore::FlattenedConstraint::ConstraintHolder::ConstraintHolder): 75 (WebCore::MediaConstraint::getMin): Deleted. 76 (WebCore::MediaConstraint::getMax): Deleted. 77 (WebCore::MediaConstraint::getExact): Deleted. 78 (WebCore::MediaConstraint::getIdeal): Deleted. 79 (WebCore::MediaConstraint::validForRange): Deleted. 80 (WebCore::MediaConstraint::find): Deleted. 81 (WebCore::MediaConstraint::fitnessDistance): Deleted. 82 (WebCore::MediaConstraint::type): Deleted. 83 84 * platform/mediastream/RealtimeMediaSource.cpp: 85 (WebCore::RealtimeMediaSource::fitnessDistance): Use downcast<>. 86 (WebCore::applyNumericConstraint): 87 (WebCore::RealtimeMediaSource::applyConstraint): Ditto. 88 (WebCore::RealtimeMediaSource::selectSettings): Ditto. Use constraints.mandatoryConstraints.filter 89 instead of direct enumeration. 90 (WebCore::RealtimeMediaSource::applyConstraints): 91 (WebCore::RealtimeMediaSource::setSampleRate): Sample rate is an int, not a double. 92 (WebCore::RealtimeMediaSource::setSampleSize): Sample size is also an int. 93 * platform/mediastream/RealtimeMediaSource.h: 94 95 * platform/mediastream/mac/AVCaptureDeviceManager.mm: 96 (WebCore::AVCaptureDeviceManager::sessionSupportsConstraint): Use downcast<>. 97 98 * platform/mock/MediaConstraintsMock.cpp: 99 (WebCore::isIntMediaConstraintSatisfiable): Use downcast<>. 100 (WebCore::isDoubleMediaConstraintSatisfiable): Ditto. 101 (WebCore::isBooleanMediaConstraintSatisfiable): Ditto. 102 (WebCore::isStringMediaConstraintSatisfiable): 103 (WebCore::isSatisfiable): 104 (WebCore::MediaConstraintsMock::verifyConstraints): Use constraints.mandatoryConstraints.filter 105 instead of direct enumeration. 106 * platform/mock/MediaConstraintsMock.h: 107 108 * platform/mock/MockRealtimeAudioSource.h: 109 * platform/mock/MockRealtimeMediaSourceCenter.cpp: 110 (WebCore::MockRealtimeMediaSourceCenter::createMediaStream): 111 1 112 2016-09-27 Wenson Hsieh <wenson_hsieh@apple.com> 2 113 -
trunk/Source/WebCore/Modules/mediastream/MediaConstraintsImpl.cpp
r204516 r206445 47 47 } 48 48 49 // FIXME: Remove after https://bugs.webkit.org/show_bug.cgi?id=16057950 void MediaConstraintsImpl::initialize(const Dictionary& constraints)51 {52 if (constraints.isUndefinedOrNull())53 return;54 }55 56 49 Ref<MediaConstraintsImpl> MediaConstraintsImpl::create(MediaTrackConstraintSetMap&& mandatoryConstraints, Vector<MediaTrackConstraintSetMap>&& advancedConstraints, bool isValid) 57 50 { -
trunk/Source/WebCore/Modules/mediastream/MediaConstraintsImpl.h
r204516 r206445 49 49 50 50 virtual ~MediaConstraintsImpl(); 51 void initialize(const Dictionary&);52 51 53 52 const MediaTrackConstraintSetMap& mandatoryConstraints() const final { return m_mandatoryConstraints; } -
trunk/Source/WebCore/bindings/js/JSMediaDevicesCustom.cpp
r206252 r206445 59 59 } 60 60 61 static RefPtr<StringConstraint> createStringConstraint(const Dictionary& mediaTrackConstraintSet, const String& name, MediaConstraintType type, ConstraintSetType constraintSetType)62 { 63 auto constraint = StringConstraint ::create(name, type);61 static Optional<StringConstraint> createStringConstraint(const Dictionary& mediaTrackConstraintSet, const String& name, MediaConstraintType type, ConstraintSetType constraintSetType) 62 { 63 auto constraint = StringConstraint(name, type); 64 64 65 65 // Dictionary constraint value. … … 72 72 String exactStringValue; 73 73 if (dictionaryValue.get("exact", exactStringValue)) 74 constraint ->setExact(exactStringValue);74 constraint.setExact(exactStringValue); 75 75 } 76 76 … … 81 81 String idealStringValue; 82 82 if (!dictionaryValue.get("ideal", idealStringValue)) 83 constraint ->setIdeal(idealStringValue);84 } 85 86 if (constraint ->isEmpty()) {83 constraint.setIdeal(idealStringValue); 84 } 85 86 if (constraint.isEmpty()) { 87 87 LOG(Media, "createStringConstraint() - ignoring string constraint '%s' with dictionary value since it has no valid or supported key/value pairs.", name.utf8().data()); 88 return nullptr;88 return Nullopt; 89 89 } 90 90 … … 97 97 initializeStringConstraintWithList(constraint, &StringConstraint::appendIdeal, arrayValue); 98 98 99 if (constraint ->isEmpty()) {99 if (constraint.isEmpty()) { 100 100 LOG(Media, "createStringConstraint() - ignoring string constraint '%s' with array value since it is empty.", name.utf8().data()); 101 return nullptr;101 return Nullopt; 102 102 } 103 103 … … 109 109 if (mediaTrackConstraintSet.get(name, value)) { 110 110 if (constraintSetType == ConstraintSetType::Mandatory) 111 constraint ->setIdeal(value);111 constraint.setIdeal(value); 112 112 else 113 constraint ->setExact(value);113 constraint.setExact(value); 114 114 115 115 return WTFMove(constraint); … … 118 118 // Invalid constraint value. 119 119 LOG(Media, "createStringConstraint() - ignoring string constraint '%s' since it has neither a dictionary nor sequence nor scalar value.", name.utf8().data()); 120 return nullptr;121 } 122 123 static RefPtr<BooleanConstraint> createBooleanConstraint(const Dictionary& mediaTrackConstraintSet, const String& name, MediaConstraintType type, ConstraintSetType constraintSetType)124 { 125 auto constraint = BooleanConstraint ::create(name, type);120 return Nullopt; 121 } 122 123 static Optional<BooleanConstraint> createBooleanConstraint(const Dictionary& mediaTrackConstraintSet, const String& name, MediaConstraintType type, ConstraintSetType constraintSetType) 124 { 125 auto constraint = BooleanConstraint(name, type); 126 126 127 127 // Dictionary constraint value. … … 130 130 bool exactValue; 131 131 if (dictionaryValue.get("exact", exactValue)) 132 constraint ->setExact(exactValue);132 constraint.setExact(exactValue); 133 133 134 134 bool idealValue; 135 135 if (dictionaryValue.get("ideal", idealValue)) 136 constraint ->setIdeal(idealValue);137 138 if (constraint ->isEmpty()) {136 constraint.setIdeal(idealValue); 137 138 if (constraint.isEmpty()) { 139 139 LOG(Media, "createBooleanConstraint() - ignoring boolean constraint '%s' with dictionary value since it has no valid or supported key/value pairs.", name.utf8().data()); 140 return nullptr;140 return Nullopt; 141 141 } 142 142 … … 148 148 if (mediaTrackConstraintSet.get(name, value)) { 149 149 if (constraintSetType == ConstraintSetType::Mandatory) 150 constraint ->setIdeal(value);150 constraint.setIdeal(value); 151 151 else 152 constraint ->setExact(value);152 constraint.setExact(value); 153 153 154 154 return WTFMove(constraint); … … 157 157 // Invalid constraint value. 158 158 LOG(Media, "createBooleanConstraint() - ignoring boolean constraint '%s' since it has neither a dictionary nor scalar value.", name.utf8().data()); 159 return nullptr;160 } 161 162 static RefPtr<DoubleConstraint> createDoubleConstraint(const Dictionary& mediaTrackConstraintSet, const String& name, MediaConstraintType type, ConstraintSetType constraintSetType)163 { 164 auto constraint = DoubleConstraint ::create(name, type);159 return Nullopt; 160 } 161 162 static Optional<DoubleConstraint> createDoubleConstraint(const Dictionary& mediaTrackConstraintSet, const String& name, MediaConstraintType type, ConstraintSetType constraintSetType) 163 { 164 auto constraint = DoubleConstraint(name, type); 165 165 166 166 // Dictionary constraint value. … … 169 169 double minValue; 170 170 if (dictionaryValue.get("min", minValue)) 171 constraint ->setMin(minValue);171 constraint.setMin(minValue); 172 172 173 173 double maxValue; 174 174 if (dictionaryValue.get("max", maxValue)) 175 constraint ->setMax(maxValue);175 constraint.setMax(maxValue); 176 176 177 177 double exactValue; 178 178 if (dictionaryValue.get("exact", exactValue)) 179 constraint ->setExact(exactValue);179 constraint.setExact(exactValue); 180 180 181 181 double idealValue; 182 182 if (dictionaryValue.get("ideal", idealValue)) 183 constraint ->setIdeal(idealValue);184 185 if (constraint ->isEmpty()) {183 constraint.setIdeal(idealValue); 184 185 if (constraint.isEmpty()) { 186 186 LOG(Media, "createDoubleConstraint() - ignoring double constraint '%s' with dictionary value since it has no valid or supported key/value pairs.", name.utf8().data()); 187 return nullptr;187 return Nullopt; 188 188 } 189 189 … … 195 195 if (mediaTrackConstraintSet.get(name, value)) { 196 196 if (constraintSetType == ConstraintSetType::Mandatory) 197 constraint ->setIdeal(value);197 constraint.setIdeal(value); 198 198 else 199 constraint ->setExact(value);199 constraint.setExact(value); 200 200 201 201 return WTFMove(constraint); … … 204 204 // Invalid constraint value. 205 205 LOG(Media, "createDoubleConstraint() - ignoring double constraint '%s' since it has neither a dictionary nor scalar value.", name.utf8().data()); 206 return nullptr;207 } 208 209 static RefPtr<IntConstraint> createIntConstraint(const Dictionary& mediaTrackConstraintSet, const String& name, MediaConstraintType type, ConstraintSetType constraintSetType)210 { 211 auto constraint = IntConstraint ::create(name, type);206 return Nullopt; 207 } 208 209 static Optional<IntConstraint> createIntConstraint(const Dictionary& mediaTrackConstraintSet, const String& name, MediaConstraintType type, ConstraintSetType constraintSetType) 210 { 211 auto constraint = IntConstraint(name, type); 212 212 213 213 // Dictionary constraint value. … … 216 216 int minValue; 217 217 if (dictionaryValue.get("min", minValue)) 218 constraint ->setMin(minValue);218 constraint.setMin(minValue); 219 219 220 220 int maxValue; 221 221 if (dictionaryValue.get("max", maxValue)) 222 constraint ->setMax(maxValue);222 constraint.setMax(maxValue); 223 223 224 224 int exactValue; 225 225 if (dictionaryValue.get("exact", exactValue)) 226 constraint ->setExact(exactValue);226 constraint.setExact(exactValue); 227 227 228 228 int idealValue; 229 229 if (dictionaryValue.get("ideal", idealValue)) 230 constraint ->setIdeal(idealValue);231 232 if (constraint ->isEmpty()) {230 constraint.setIdeal(idealValue); 231 232 if (constraint.isEmpty()) { 233 233 LOG(Media, "createIntConstraint() - ignoring long constraint '%s' with dictionary value since it has no valid or supported key/value pairs.", name.utf8().data()); 234 return nullptr;234 return Nullopt; 235 235 } 236 236 … … 242 242 if (mediaTrackConstraintSet.get(name, value)) { 243 243 if (constraintSetType == ConstraintSetType::Mandatory) 244 constraint ->setIdeal(value);244 constraint.setIdeal(value); 245 245 else 246 constraint ->setExact(value);246 constraint.setExact(value); 247 247 248 248 return WTFMove(constraint); … … 251 251 // Invalid constraint value. 252 252 LOG(Media, "createIntConstraint() - ignoring long constraint '%s' since it has neither a dictionary nor scalar value.", name.utf8().data()); 253 return nullptr;253 return Nullopt; 254 254 } 255 255 … … 257 257 { 258 258 MediaConstraintType constraintType = RealtimeMediaSourceSupportedConstraints::constraintFromName(name); 259 260 RefPtr<MediaConstraint> mediaConstraint;261 259 switch (constraintType) { 262 260 case MediaConstraintType::Width: 261 map.set(constraintType, createIntConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType)); 262 break; 263 263 case MediaConstraintType::Height: 264 map.set(constraintType, createIntConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType)); 265 break; 264 266 case MediaConstraintType::SampleRate: 267 map.set(constraintType, createIntConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType)); 268 break; 265 269 case MediaConstraintType::SampleSize: 266 m ediaConstraint = createIntConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType);270 map.set(constraintType, createIntConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType)); 267 271 break; 268 272 269 273 case MediaConstraintType::AspectRatio: 274 map.set(constraintType, createDoubleConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType)); 275 break; 270 276 case MediaConstraintType::FrameRate: 277 map.set(constraintType, createDoubleConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType)); 278 break; 271 279 case MediaConstraintType::Volume: 272 m ediaConstraint = createDoubleConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType);280 map.set(constraintType, createDoubleConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType)); 273 281 break; 274 282 275 283 case MediaConstraintType::EchoCancellation: 276 m ediaConstraint = createBooleanConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType);284 map.set(constraintType, createBooleanConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType)); 277 285 break; 278 286 279 287 case MediaConstraintType::FacingMode: 288 map.set(constraintType, createStringConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType)); 289 break; 280 290 case MediaConstraintType::DeviceId: 291 map.set(constraintType, createStringConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType)); 292 break; 281 293 case MediaConstraintType::GroupId: 282 m ediaConstraint = createStringConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType);294 map.set(constraintType, createStringConstraint(mediaTrackConstraintSet, name, constraintType, constraintSetType)); 283 295 break; 284 296 285 297 case MediaConstraintType::Unknown: 286 LOG(Media, "parseMediaTrackConstraintSetForKey() - found unsupported constraint '%s'.", name.utf8().data()); 287 mediaConstraint = UnknownConstraint::create(name, constraintType); 288 break; 289 } 290 291 map.add(name, WTFMove(mediaConstraint)); 298 LOG(Media, "parseMediaTrackConstraintSetForKey() - ignoring unsupported constraint '%s'.", name.utf8().data()); 299 return; 300 } 292 301 } 293 302 -
trunk/Source/WebCore/platform/mediastream/CaptureDeviceManager.cpp
r205929 r206445 73 73 bool CaptureDeviceManager::verifyConstraintsForMediaType(RealtimeMediaSource::Type type, const MediaConstraints& constraints, const CaptureSessionInfo* session, String& invalidConstraint) 74 74 { 75 auto& mandatoryConstraints = constraints.mandatoryConstraints(); 76 for (auto& nameConstraintPair : mandatoryConstraints) { 77 if (sessionSupportsConstraint(session, type, *nameConstraintPair.value)) 78 continue; 79 80 invalidConstraint = nameConstraintPair.key; 75 invalidConstraint = emptyString(); 76 constraints.mandatoryConstraints().filter([&](const MediaConstraint& constraint) { 77 if (!sessionSupportsConstraint(session, type, constraint)) { 78 invalidConstraint = constraint.name(); 79 return true; 80 } 81 81 82 return false; 82 } 83 84 return true; 83 }); 84 85 return invalidConstraint.isEmpty(); 86 85 87 } 86 88 … … 154 156 { 155 157 const RealtimeMediaSourceSupportedConstraints& supportedConstraints = RealtimeMediaSourceCenter::singleton().supportedConstraints(); 156 MediaConstraintType constraintType = constraint. type();158 MediaConstraintType constraintType = constraint.constraintType(); 157 159 if (!supportedConstraints.supportsConstraint(constraintType)) 158 160 return false; … … 177 179 // FIXME: https://bugs.webkit.org/show_bug.cgi?id=160793. Handle sequence of facingMode constraints. 178 180 Vector<String> exactFacingMode; 179 if (! constraint.getExact(exactFacingMode))181 if (!downcast<const StringConstraint>(constraint).getExact(exactFacingMode)) 180 182 return false; 181 183 … … 193 195 194 196 int min = 0; 195 if ( constraint.getMin(min))197 if (downcast<const IntConstraint>(constraint).getMin(min)) 196 198 isSupported &= min > 60; 197 199 198 200 int max = 60; 199 if ( constraint.getMax(max))201 if (downcast<const IntConstraint>(constraint).getMax(max)) 200 202 isSupported &= max < min; 201 203 202 204 int exact; 203 if ( constraint.getExact(exact))205 if (downcast<const IntConstraint>(constraint).getExact(exact)) 204 206 isSupported &= (exact < min || exact > max); 205 207 -
trunk/Source/WebCore/platform/mediastream/MediaConstraints.cpp
r205965 r206445 35 35 #include "RealtimeMediaSourceCenter.h" 36 36 #include "RealtimeMediaSourceSupportedConstraints.h" 37 #include <wtf/StdLibExtras.h> 37 38 38 39 namespace WebCore { 39 40 Ref<MediaConstraint> MediaConstraint::create(const String& name)41 {42 MediaConstraintType constraintType = RealtimeMediaSourceSupportedConstraints::constraintFromName(name);43 44 switch (constraintType) {45 case MediaConstraintType::Width:46 case MediaConstraintType::Height:47 case MediaConstraintType::SampleRate:48 case MediaConstraintType::SampleSize:49 return IntConstraint::create(name, constraintType);50 case MediaConstraintType::AspectRatio:51 case MediaConstraintType::FrameRate:52 case MediaConstraintType::Volume:53 return DoubleConstraint::create(name, constraintType);54 case MediaConstraintType::EchoCancellation:55 return BooleanConstraint::create(name, constraintType);56 case MediaConstraintType::FacingMode:57 case MediaConstraintType::DeviceId:58 case MediaConstraintType::GroupId:59 return StringConstraint::create(name, constraintType);60 case MediaConstraintType::Unknown:61 return UnknownConstraint::create(name, constraintType);62 }63 64 ASSERT_NOT_REACHED();65 return MediaConstraint::create(String());66 }67 68 Ref<MediaConstraint> MediaConstraint::copy() const69 {70 return MediaConstraint::create(name());71 }72 73 Ref<MediaConstraint> IntConstraint::copy() const74 {75 auto copy = IntConstraint::create(name(), type());76 copy->m_min = m_min;77 copy->m_max = m_max;78 copy->m_exact = m_exact;79 copy->m_ideal = m_ideal;80 81 return copy.leakRef();82 }83 84 Ref<MediaConstraint> DoubleConstraint::copy() const85 {86 auto copy = DoubleConstraint::create(name(), type());87 copy->m_min = m_min;88 copy->m_max = m_max;89 copy->m_exact = m_exact;90 copy->m_ideal = m_ideal;91 92 return copy.leakRef();93 }94 95 Ref<MediaConstraint> BooleanConstraint::copy() const96 {97 auto copy = BooleanConstraint::create(name(), type());98 copy->m_exact = m_exact;99 copy->m_ideal = m_ideal;100 101 return copy.leakRef();102 }103 104 Ref<MediaConstraint> StringConstraint::copy() const105 {106 auto copy = StringConstraint::create(name(), type());107 copy->m_exact = m_exact;108 copy->m_ideal = m_ideal;109 110 return copy.leakRef();111 }112 40 113 41 bool BooleanConstraint::getExact(bool& exact) const … … 170 98 } 171 99 172 const String& StringConstraint::find(std::function<bool( ConstraintType,const String&)> filter) const100 const String& StringConstraint::find(std::function<bool(const String&)> filter) const 173 101 { 174 102 for (auto& constraint : m_exact) { 175 if (filter( ConstraintType::ExactConstraint,constraint))103 if (filter(constraint)) 176 104 return constraint; 177 105 } 178 106 179 107 for (auto& constraint : m_ideal) { 180 if (filter( ConstraintType::IdealConstraint,constraint))108 if (filter(constraint)) 181 109 return constraint; 182 110 } … … 223 151 void StringConstraint::merge(const MediaConstraint& other) 224 152 { 153 ASSERT(other.isString()); 154 const StringConstraint& typedOther = downcast<StringConstraint>(other); 155 225 156 if (other.isEmpty()) 226 157 return; 227 158 228 159 Vector<String> values; 229 if ( other.getExact(values)) {160 if (typedOther.getExact(values)) { 230 161 if (m_exact.isEmpty()) 231 162 m_exact = values; … … 238 169 } 239 170 240 if ( other.getIdeal(values)) {171 if (typedOther.getIdeal(values)) { 241 172 if (m_ideal.isEmpty()) 242 173 m_ideal = values; … … 252 183 void FlattenedConstraint::set(const MediaConstraint& constraint) 253 184 { 254 for (auto existingConstraint : m_constraints) { 255 if (existingConstraint->type() == constraint.type()) { 256 existingConstraint = constraint.copy(); 185 for (auto& variant : m_variants) { 186 if (variant.constraintType() == constraint.constraintType()) 187 return; 188 } 189 190 append(constraint); 191 } 192 193 void FlattenedConstraint::merge(const MediaConstraint& constraint) 194 { 195 for (auto& variant : *this) { 196 if (variant.constraintType() != constraint.constraintType()) 197 continue; 198 199 switch (variant.dataType()) { 200 case MediaConstraint::DataType::Integer: 201 ASSERT(constraint.isInt()); 202 downcast<const IntConstraint>(variant).merge(downcast<const IntConstraint>(constraint)); 203 return; 204 case MediaConstraint::DataType::Double: 205 ASSERT(constraint.isDouble()); 206 downcast<const DoubleConstraint>(variant).merge(downcast<const DoubleConstraint>(constraint)); 207 return; 208 case MediaConstraint::DataType::Boolean: 209 ASSERT(constraint.isBoolean()); 210 downcast<const BooleanConstraint>(variant).merge(downcast<const BooleanConstraint>(constraint)); 211 return; 212 case MediaConstraint::DataType::String: 213 ASSERT(constraint.isString()); 214 downcast<const StringConstraint>(variant).merge(downcast<const StringConstraint>(constraint)); 215 return; 216 case MediaConstraint::DataType::None: 217 ASSERT_NOT_REACHED(); 257 218 return; 258 219 } 259 220 } 260 221 261 m_constraints.append(constraint.copy()); 262 } 263 264 void FlattenedConstraint::merge(const MediaConstraint& constraint) 265 { 266 for (auto existingConstraint : m_constraints) { 267 if (existingConstraint->type() == constraint.type()) { 268 existingConstraint->merge(constraint); 269 return; 270 } 271 } 272 273 m_constraints.append(constraint.copy()); 222 append(constraint); 223 } 224 225 void FlattenedConstraint::append(const MediaConstraint& constraint) 226 { 227 #ifndef NDEBUG 228 ++m_generation; 229 #endif 230 231 m_variants.append(ConstraintHolder::create(constraint)); 232 233 } 234 235 void MediaTrackConstraintSetMap::forEach(std::function<void(const MediaConstraint&)> callback) const 236 { 237 if (m_width && !m_width->isEmpty()) 238 callback(*m_width); 239 if (m_height && !m_height->isEmpty()) 240 callback(*m_height); 241 if (m_sampleRate && !m_sampleRate->isEmpty()) 242 callback(*m_sampleRate); 243 if (m_sampleSize && !m_sampleSize->isEmpty()) 244 callback(*m_sampleSize); 245 246 if (m_aspectRatio && !m_aspectRatio->isEmpty()) 247 callback(*m_aspectRatio); 248 if (m_frameRate && !m_frameRate->isEmpty()) 249 callback(*m_frameRate); 250 if (m_volume && !m_volume->isEmpty()) 251 callback(*m_volume); 252 253 if (m_echoCancellation && !m_echoCancellation->isEmpty()) 254 callback(*m_echoCancellation); 255 256 if (m_facingMode && !m_facingMode->isEmpty()) 257 callback(*m_facingMode); 258 if (m_deviceId && !m_deviceId->isEmpty()) 259 callback(*m_deviceId); 260 if (m_groupId && !m_groupId->isEmpty()) 261 callback(*m_groupId); 262 } 263 264 void MediaTrackConstraintSetMap::filter(std::function<bool(const MediaConstraint&)> callback) const 265 { 266 if (m_width && !m_width->isEmpty() && callback(*m_width)) 267 return; 268 if (m_height && !m_height->isEmpty() && callback(*m_height)) 269 return; 270 if (m_sampleRate && !m_sampleRate->isEmpty() && callback(*m_sampleRate)) 271 return; 272 if (m_sampleSize && !m_sampleSize->isEmpty() && callback(*m_sampleSize)) 273 return; 274 275 if (m_aspectRatio && !m_aspectRatio->isEmpty() && callback(*m_aspectRatio)) 276 return; 277 if (m_frameRate && !m_frameRate->isEmpty() && callback(*m_frameRate)) 278 return; 279 if (m_volume && !m_volume->isEmpty() && callback(*m_volume)) 280 return; 281 282 if (m_echoCancellation && !m_echoCancellation->isEmpty() && callback(*m_echoCancellation)) 283 return; 284 285 if (m_facingMode && !m_facingMode->isEmpty() && callback(*m_facingMode)) 286 return; 287 if (m_deviceId && !m_deviceId->isEmpty() && callback(*m_deviceId)) 288 return; 289 if (m_groupId && !m_groupId->isEmpty() && callback(*m_groupId)) 290 return; 291 } 292 293 bool MediaTrackConstraintSetMap::isEmpty() const 294 { 295 return (!m_width || m_width->isEmpty()) 296 && (!m_height || m_height->isEmpty()) 297 && (!m_sampleRate || m_sampleRate->isEmpty()) 298 && (!m_sampleSize || m_sampleSize->isEmpty()) 299 && (!m_aspectRatio || m_aspectRatio->isEmpty()) 300 && (!m_frameRate || m_frameRate->isEmpty()) 301 && (!m_volume || m_volume->isEmpty()) 302 && (!m_echoCancellation || m_echoCancellation->isEmpty()) 303 && (!m_facingMode || m_facingMode->isEmpty()) 304 && (!m_deviceId || m_deviceId->isEmpty()) 305 && (!m_groupId || m_groupId->isEmpty()); 306 } 307 308 void MediaTrackConstraintSetMap::set(MediaConstraintType constraintType, Optional<IntConstraint>&& constraint) 309 { 310 switch (constraintType) { 311 case MediaConstraintType::Width: 312 m_width = WTFMove(constraint); 313 break; 314 case MediaConstraintType::Height: 315 m_height = WTFMove(constraint); 316 break; 317 case MediaConstraintType::SampleRate: 318 m_sampleRate = WTFMove(constraint); 319 break; 320 case MediaConstraintType::SampleSize: 321 m_sampleSize = WTFMove(constraint); 322 break; 323 324 case MediaConstraintType::AspectRatio: 325 case MediaConstraintType::FrameRate: 326 case MediaConstraintType::Volume: 327 case MediaConstraintType::EchoCancellation: 328 case MediaConstraintType::FacingMode: 329 case MediaConstraintType::DeviceId: 330 case MediaConstraintType::GroupId: 331 case MediaConstraintType::Unknown: 332 ASSERT_NOT_REACHED(); 333 break; 334 } 335 } 336 337 void MediaTrackConstraintSetMap::set(MediaConstraintType constraintType, Optional<DoubleConstraint>&& constraint) 338 { 339 switch (constraintType) { 340 case MediaConstraintType::AspectRatio: 341 m_aspectRatio = WTFMove(constraint); 342 break; 343 case MediaConstraintType::FrameRate: 344 m_frameRate = WTFMove(constraint); 345 break; 346 case MediaConstraintType::Volume: 347 m_volume = WTFMove(constraint); 348 break; 349 350 case MediaConstraintType::Width: 351 case MediaConstraintType::Height: 352 case MediaConstraintType::SampleRate: 353 case MediaConstraintType::SampleSize: 354 case MediaConstraintType::EchoCancellation: 355 case MediaConstraintType::FacingMode: 356 case MediaConstraintType::DeviceId: 357 case MediaConstraintType::GroupId: 358 case MediaConstraintType::Unknown: 359 ASSERT_NOT_REACHED(); 360 break; 361 } 362 } 363 364 void MediaTrackConstraintSetMap::set(MediaConstraintType constraintType, Optional<BooleanConstraint>&& constraint) 365 { 366 switch (constraintType) { 367 case MediaConstraintType::EchoCancellation: 368 m_echoCancellation = WTFMove(constraint); 369 break; 370 371 case MediaConstraintType::Width: 372 case MediaConstraintType::Height: 373 case MediaConstraintType::SampleRate: 374 case MediaConstraintType::SampleSize: 375 case MediaConstraintType::AspectRatio: 376 case MediaConstraintType::FrameRate: 377 case MediaConstraintType::Volume: 378 case MediaConstraintType::FacingMode: 379 case MediaConstraintType::DeviceId: 380 case MediaConstraintType::GroupId: 381 case MediaConstraintType::Unknown: 382 ASSERT_NOT_REACHED(); 383 break; 384 } 385 } 386 387 void MediaTrackConstraintSetMap::set(MediaConstraintType constraintType, Optional<StringConstraint>&& constraint) 388 { 389 switch (constraintType) { 390 case MediaConstraintType::FacingMode: 391 m_facingMode = WTFMove(constraint); 392 break; 393 case MediaConstraintType::DeviceId: 394 m_deviceId = WTFMove(constraint); 395 break; 396 case MediaConstraintType::GroupId: 397 m_groupId = WTFMove(constraint); 398 break; 399 400 case MediaConstraintType::Width: 401 case MediaConstraintType::Height: 402 case MediaConstraintType::SampleRate: 403 case MediaConstraintType::SampleSize: 404 case MediaConstraintType::AspectRatio: 405 case MediaConstraintType::FrameRate: 406 case MediaConstraintType::Volume: 407 case MediaConstraintType::EchoCancellation: 408 case MediaConstraintType::Unknown: 409 ASSERT_NOT_REACHED(); 410 break; 411 } 274 412 } 275 413 -
trunk/Source/WebCore/platform/mediastream/MediaConstraints.h
r205574 r206445 39 39 #include <wtf/HashMap.h> 40 40 #include <wtf/RefCounted.h> 41 #include <wtf/Variant.h> 41 42 #include <wtf/text/StringHash.h> 42 43 #include <wtf/text/WTFString.h> … … 44 45 namespace WebCore { 45 46 46 class MediaConstraint : public RefCounted<MediaConstraint> { 47 public: 48 static Ref<MediaConstraint> create(const String&); 49 50 enum class ConstraintType { ExactConstraint, IdealConstraint, MinConstraint, MaxConstraint }; 47 class MediaConstraint { 48 public: 49 enum class DataType { None, Integer, Double, Boolean, String }; 51 50 52 51 virtual ~MediaConstraint() { }; 53 52 54 virtual Ref<MediaConstraint> copy() const; 55 virtual bool isEmpty() const = 0; 56 virtual bool isMandatory() const = 0; 57 58 virtual bool getMin(int&) const { ASSERT_NOT_REACHED(); return false; } 59 virtual bool getMax(int&) const { ASSERT_NOT_REACHED(); return false; } 60 virtual bool getExact(int&) const { ASSERT_NOT_REACHED(); return false; } 61 virtual bool getIdeal(int&) const { ASSERT_NOT_REACHED(); return false; } 62 virtual bool validForRange(int, int) const { ASSERT_NOT_REACHED(); return false; } 63 virtual int find(std::function<bool(ConstraintType, int)>) const { ASSERT_NOT_REACHED(); return 0; } 64 virtual double fitnessDistance(int, int) const { ASSERT_NOT_REACHED(); return 0; } 65 66 virtual bool getMin(double&) const { ASSERT_NOT_REACHED(); return false; } 67 virtual bool getMax(double&) const { ASSERT_NOT_REACHED(); return false; } 68 virtual bool getExact(double&) const { ASSERT_NOT_REACHED(); return false; } 69 virtual bool getIdeal(double&) const { ASSERT_NOT_REACHED(); return false; } 70 virtual bool validForRange(double, double) const { ASSERT_NOT_REACHED(); return false; } 71 virtual double find(std::function<bool(ConstraintType, double)>) const { ASSERT_NOT_REACHED(); return 0; } 72 virtual double fitnessDistance(double, double) const { ASSERT_NOT_REACHED(); return 0; } 73 74 virtual bool getMin(bool&) const { ASSERT_NOT_REACHED(); return false; } 75 virtual bool getMax(bool&) const { ASSERT_NOT_REACHED(); return false; } 76 virtual bool getExact(bool&) const { ASSERT_NOT_REACHED(); return false; } 77 virtual bool getIdeal(bool&) const { ASSERT_NOT_REACHED(); return false; } 78 virtual double fitnessDistance(bool) const { ASSERT_NOT_REACHED(); return 0; } 79 80 virtual bool getMin(Vector<String>&) const { ASSERT_NOT_REACHED(); return false; } 81 virtual bool getMax(Vector<String>&) const { ASSERT_NOT_REACHED(); return false; } 82 virtual bool getExact(Vector<String>&) const { ASSERT_NOT_REACHED(); return false; } 83 virtual bool getIdeal(Vector<String>&) const { ASSERT_NOT_REACHED(); return false; } 84 virtual const String& find(std::function<bool(ConstraintType, const String&)>) const { ASSERT_NOT_REACHED(); return emptyString(); } 85 86 virtual double fitnessDistance(const String&) const { ASSERT_NOT_REACHED(); return 0; } 87 virtual double fitnessDistance(const Vector<String>&) const { ASSERT_NOT_REACHED(); return 0; } 88 89 virtual void merge(const MediaConstraint&) { ASSERT_NOT_REACHED(); } 90 91 MediaConstraintType type() const { return m_type; } 53 virtual bool isEmpty() const { return true; } 54 virtual bool isMandatory() const { return false; } 55 virtual void merge(const MediaConstraint&) { } 56 57 bool isInt() const { return m_dataType == DataType::Integer; } 58 bool isDouble() const { return m_dataType == DataType::Double; } 59 bool isBoolean() const { return m_dataType == DataType::Boolean; } 60 bool isString() const { return m_dataType == DataType::String; } 61 62 DataType dataType() const { return m_dataType; } 63 MediaConstraintType constraintType() const { return m_constraintType; } 92 64 const String& name() const { return m_name; } 93 65 94 66 protected: 95 explicit MediaConstraint(const String& name, MediaConstraintType type)67 explicit MediaConstraint(const AtomicString& name, MediaConstraintType constraintType, DataType dataType) 96 68 : m_name(name) 97 , m_type(type) 98 { 99 } 69 , m_constraintType(constraintType) 70 , m_dataType(dataType) 71 { 72 } 73 100 74 101 75 private: 102 String m_name; 103 MediaConstraintType m_type; 76 AtomicString m_name; 77 MediaConstraintType m_constraintType; 78 DataType m_dataType; 104 79 }; 105 80 … … 107 82 class NumericConstraint : public MediaConstraint { 108 83 public: 109 bool isEmpty() const override { return !m_min && !m_max && !m_exact && !m_ideal; }110 bool isMandatory() const override { return m_min || m_max || m_exact; }111 112 84 void setMin(ValueType value) { m_min = value; } 113 85 void setMax(ValueType value) { m_max = value; } … … 115 87 void setIdeal(ValueType value) { m_ideal = value; } 116 88 117 bool getMin(ValueType& min) const final { 89 bool getMin(ValueType& min) const 90 { 118 91 if (!m_min) 119 92 return false; … … 123 96 } 124 97 125 bool getMax(ValueType& max) const final { 98 bool getMax(ValueType& max) const 99 { 126 100 if (!m_max) 127 101 return false; … … 131 105 } 132 106 133 bool getExact(ValueType& exact) const final { 107 bool getExact(ValueType& exact) const 108 { 134 109 if (!m_exact) 135 110 return false; … … 139 114 } 140 115 141 bool getIdeal(ValueType& ideal) const final { 116 bool getIdeal(ValueType& ideal) const 117 { 142 118 if (!m_ideal) 143 119 return false; … … 155 131 } 156 132 157 double fitnessDistance(ValueType rangeMin, ValueType rangeMax) const final { 133 double fitnessDistance(ValueType rangeMin, ValueType rangeMax) const 134 { 158 135 // https://w3c.github.io/mediacapture-main/#dfn-applyconstraints 159 136 // 1. If the constraint is not supported by the browser, the fitness distance is 0. … … 190 167 } 191 168 192 void merge(const MediaConstraint& other) final { 169 bool validForRange(ValueType rangeMin, ValueType rangeMax) const 170 { 171 if (isEmpty()) 172 return false; 173 174 if (m_exact) { 175 const ValueType exact = m_exact.value(); 176 if (exact < rangeMin && !nearlyEqual(exact, rangeMin)) 177 return false; 178 if (exact > rangeMax && !nearlyEqual(exact, rangeMax)) 179 return false; 180 } 181 182 if (m_min) { 183 const ValueType constraintMin = m_min.value(); 184 if (constraintMin > rangeMax && !nearlyEqual(constraintMin, rangeMax)) 185 return false; 186 } 187 188 189 if (m_max) { 190 const ValueType constraintMax = m_max.value(); 191 if (constraintMax < rangeMin && !nearlyEqual(constraintMax, rangeMin)) 192 return false; 193 } 194 195 return true; 196 } 197 198 ValueType find(std::function<bool(ValueType)> function) const 199 { 200 if (m_min && function(m_min.value())) 201 return m_min.value(); 202 203 if (m_max && function(m_max.value())) 204 return m_max.value(); 205 206 if (m_exact && function(m_exact.value())) 207 return m_exact.value(); 208 209 if (m_ideal && function(m_ideal.value())) 210 return m_ideal.value(); 211 212 return 0; 213 } 214 215 bool isEmpty() const override { return !m_min && !m_max && !m_exact && !m_ideal; } 216 bool isMandatory() const override { return m_min || m_max || m_exact; } 217 218 protected: 219 explicit NumericConstraint(const AtomicString& name, MediaConstraintType type, DataType dataType) 220 : MediaConstraint(name, type, dataType) 221 { 222 } 223 224 void innerMerge(const NumericConstraint& other) 225 { 193 226 if (other.isEmpty()) 194 227 return; … … 215 248 } 216 249 217 bool validForRange(ValueType rangeMin, ValueType rangeMax) const final {218 if (isEmpty())219 return false;220 221 if (m_exact) {222 const ValueType exact = m_exact.value();223 if (exact < rangeMin && !nearlyEqual(exact, rangeMin))224 return false;225 if (exact > rangeMax && !nearlyEqual(exact, rangeMax))226 return false;227 }228 229 if (m_min) {230 const ValueType constraintMin = m_min.value();231 if (constraintMin > rangeMax && !nearlyEqual(constraintMin, rangeMax))232 return false;233 }234 235 236 if (m_max) {237 const ValueType constraintMax = m_max.value();238 if (constraintMax < rangeMin && !nearlyEqual(constraintMax, rangeMin))239 return false;240 }241 242 return true;243 }244 245 ValueType find(std::function<bool(ConstraintType, ValueType)> function) const final {246 if (m_min && function(ConstraintType::MinConstraint, m_min.value()))247 return m_min.value();248 249 if (m_max && function(ConstraintType::MaxConstraint, m_max.value()))250 return m_max.value();251 252 if (m_exact && function(ConstraintType::ExactConstraint, m_exact.value()))253 return m_exact.value();254 255 if (m_ideal && function(ConstraintType::IdealConstraint, m_ideal.value()))256 return m_ideal.value();257 258 return 0;259 }260 261 262 protected:263 explicit NumericConstraint(const String& name, MediaConstraintType type)264 : MediaConstraint(name, type)265 {266 }267 268 250 Optional<ValueType> m_min; 269 251 Optional<ValueType> m_max; … … 274 256 class IntConstraint final : public NumericConstraint<int> { 275 257 public: 276 static Ref<IntConstraint> create(const String& name, MediaConstraintType type) { return adoptRef(*new IntConstraint(name, type)); }277 278 Ref<MediaConstraint> copy() const final;279 280 private: 281 explicit IntConstraint(const String& name, MediaConstraintType type)282 : NumericConstraint<int>(name, type)283 {258 explicit IntConstraint(const AtomicString& name, MediaConstraintType type) 259 : NumericConstraint<int>(name, type, DataType::Integer) 260 { 261 } 262 263 void merge(const MediaConstraint& other) final { 264 ASSERT(other.isInt()); 265 NumericConstraint::innerMerge(downcast<const IntConstraint>(other)); 284 266 } 285 267 }; … … 287 269 class DoubleConstraint final : public NumericConstraint<double> { 288 270 public: 289 static Ref<DoubleConstraint> create(const String& name, MediaConstraintType type) { return adoptRef(*new DoubleConstraint(name, type)); }290 291 Ref<MediaConstraint> copy() const final;292 293 private: 294 explicit DoubleConstraint(const String& name, MediaConstraintType type)295 : NumericConstraint<double>(name, type)296 {271 explicit DoubleConstraint(const AtomicString& name, MediaConstraintType type) 272 : NumericConstraint<double>(name, type, DataType::Double) 273 { 274 } 275 276 void merge(const MediaConstraint& other) final { 277 ASSERT(other.isDouble()); 278 NumericConstraint::innerMerge(downcast<DoubleConstraint>(other)); 297 279 } 298 280 }; … … 300 282 class BooleanConstraint final : public MediaConstraint { 301 283 public: 302 static Ref<BooleanConstraint> create(const String& name, MediaConstraintType type) { return adoptRef(*new BooleanConstraint(name, type)); } 303 304 Ref<MediaConstraint> copy() const final; 284 explicit BooleanConstraint(const AtomicString& name, MediaConstraintType type) 285 : MediaConstraint(name, type, DataType::Boolean) 286 { 287 } 305 288 306 289 void setExact(bool value) { m_exact = value; } 307 290 void setIdeal(bool value) { m_ideal = value; } 308 291 309 bool getExact(bool&) const final; 310 bool getIdeal(bool&) const final; 311 312 bool isEmpty() const final { return !m_exact && !m_ideal; }; 313 bool isMandatory() const final { return bool(m_exact); } 314 315 double fitnessDistance(bool value) const final { 292 bool getExact(bool&) const; 293 bool getIdeal(bool&) const; 294 295 double fitnessDistance(bool value) const 296 { 316 297 // https://w3c.github.io/mediacapture-main/#dfn-applyconstraints 317 298 // 1. If the constraint is not supported by the browser, the fitness distance is 0. … … 336 317 337 318 void merge(const MediaConstraint& other) final { 338 if (other.isEmpty()) 319 ASSERT(other.isBoolean()); 320 const BooleanConstraint& typedOther = downcast<BooleanConstraint>(other); 321 322 if (typedOther.isEmpty()) 339 323 return; 340 324 341 325 bool value; 342 if ( other.getExact(value))326 if (typedOther.getExact(value)) 343 327 m_exact = value; 344 328 345 if ( other.getIdeal(value)) {329 if (typedOther.getIdeal(value)) { 346 330 if (!m_ideal || (value && !m_ideal.value())) 347 331 m_ideal = value; … … 349 333 } 350 334 335 bool isEmpty() const final { return !m_exact && !m_ideal; }; 336 bool isMandatory() const final { return bool(m_exact); } 337 351 338 private: 352 explicit BooleanConstraint(const String& name, MediaConstraintType type)353 : MediaConstraint(name, type)354 {355 }356 357 339 Optional<bool> m_exact; 358 340 Optional<bool> m_ideal; … … 361 343 class StringConstraint final : public MediaConstraint { 362 344 public: 363 static Ref<StringConstraint> create(const String& name, MediaConstraintType type) { return adoptRef(*new StringConstraint(name, type)); } 364 365 Ref<MediaConstraint> copy() const final; 345 explicit StringConstraint(const AtomicString& name, MediaConstraintType type) 346 : MediaConstraint(name, type, DataType::String) 347 { 348 } 366 349 367 350 void setExact(const String&); … … 370 353 void appendIdeal(const String&); 371 354 372 bool getExact(Vector<String>&) const final; 373 bool getIdeal(Vector<String>&) const final; 355 bool getExact(Vector<String>&) const; 356 bool getIdeal(Vector<String>&) const; 357 358 double fitnessDistance(const String&) const; 359 double fitnessDistance(const Vector<String>&) const; 360 361 const String& find(std::function<bool(const String&)>) const; 362 void merge(const MediaConstraint&) final; 374 363 375 364 bool isEmpty() const final { return m_exact.isEmpty() && m_ideal.isEmpty(); } 376 365 bool isMandatory() const final { return !m_exact.isEmpty(); } 377 366 378 double fitnessDistance(const String&) const final;379 double fitnessDistance(const Vector<String>&) const final;380 381 const String& find(std::function<bool(ConstraintType, const String&)>) const final;382 void merge(const MediaConstraint&) final;383 384 367 private: 385 explicit StringConstraint(const String& name, MediaConstraintType type)386 : MediaConstraint(name, type)387 {388 }389 390 368 Vector<String> m_exact; 391 369 Vector<String> m_ideal; … … 394 372 class UnknownConstraint final : public MediaConstraint { 395 373 public: 396 static Ref<UnknownConstraint> create(const String& name, MediaConstraintType type) { return adoptRef(*new UnknownConstraint(name, type)); } 397 374 explicit UnknownConstraint(const AtomicString& name, MediaConstraintType type) 375 : MediaConstraint(name, type, DataType::None) 376 { 377 } 378 379 private: 398 380 bool isEmpty() const final { return true; } 399 381 bool isMandatory() const final { return false; } 382 void merge(const MediaConstraint&) final { } 383 }; 384 385 class MediaTrackConstraintSetMap { 386 public: 387 void forEach(std::function<void(const MediaConstraint&)>) const; 388 void filter(std::function<bool(const MediaConstraint&)>) const; 389 bool isEmpty() const; 390 391 void set(MediaConstraintType, Optional<IntConstraint>&&); 392 void set(MediaConstraintType, Optional<DoubleConstraint>&&); 393 void set(MediaConstraintType, Optional<BooleanConstraint>&&); 394 void set(MediaConstraintType, Optional<StringConstraint>&&); 400 395 401 396 private: 402 explicit UnknownConstraint(const String& name, MediaConstraintType type) 403 : MediaConstraint(name, type) 404 { 405 } 406 }; 407 408 using MediaTrackConstraintSetMap = HashMap<String, RefPtr<MediaConstraint>>; 397 Optional<IntConstraint> m_width; 398 Optional<IntConstraint> m_height; 399 Optional<IntConstraint> m_sampleRate; 400 Optional<IntConstraint> m_sampleSize; 401 402 Optional<DoubleConstraint> m_aspectRatio; 403 Optional<DoubleConstraint> m_frameRate; 404 Optional<DoubleConstraint> m_volume; 405 406 Optional<BooleanConstraint> m_echoCancellation; 407 408 Optional<StringConstraint> m_facingMode; 409 Optional<StringConstraint> m_deviceId; 410 Optional<StringConstraint> m_groupId; 411 }; 409 412 410 413 class FlattenedConstraint { 411 414 public: 412 typedef Vector<RefPtr<MediaConstraint>>::const_iterator const_iterator;413 415 414 416 void set(const MediaConstraint&); 415 417 void merge(const MediaConstraint&); 416 bool isEmpty() const { return m_constraints.isEmpty(); } 417 418 const_iterator begin() const { return m_constraints.begin(); } 419 const_iterator end() const { return m_constraints.end(); } 418 void append(const MediaConstraint&); 419 bool isEmpty() const { return m_variants.isEmpty(); } 420 421 class iterator { 422 public: 423 iterator(const FlattenedConstraint* constraint, size_t index) 424 : m_constraint(constraint) 425 , m_index(index) 426 #ifndef NDEBUG 427 , m_generation(constraint->m_generation) 428 #endif 429 { 430 } 431 432 MediaConstraint& operator*() const 433 { 434 return m_constraint->m_variants.at(m_index).constraint(); 435 } 436 437 iterator& operator++() 438 { 439 #ifndef NDEBUG 440 ASSERT(m_generation == m_constraint->m_generation); 441 #endif 442 m_index++; 443 return *this; 444 } 445 446 bool operator==(const iterator& other) const { return m_index == other.m_index; } 447 bool operator!=(const iterator& other) const { return !(*this == other); } 448 449 private: 450 const FlattenedConstraint* m_constraint { nullptr }; 451 size_t m_index { 0 }; 452 #ifndef NDEBUG 453 int m_generation { 0 }; 454 #endif 455 }; 456 457 const iterator begin() const { return iterator(this, 0); } 458 const iterator end() const { return iterator(this, m_variants.size()); } 420 459 421 460 private: 422 423 Vector<RefPtr<MediaConstraint>> m_constraints; 461 class ConstraintHolder { 462 public: 463 static ConstraintHolder& create(const MediaConstraint& value) { return *new ConstraintHolder(value); } 464 465 ~ConstraintHolder() 466 { 467 switch (dataType()) { 468 case MediaConstraint::DataType::Integer: 469 delete m_value.asInteger; 470 break; 471 case MediaConstraint::DataType::Double: 472 delete m_value.asDouble; 473 break; 474 case MediaConstraint::DataType::Boolean: 475 delete m_value.asBoolean; 476 break; 477 case MediaConstraint::DataType::String: 478 delete m_value.asString; 479 break; 480 case MediaConstraint::DataType::None: 481 ASSERT_NOT_REACHED(); 482 break; 483 } 484 485 #ifndef NDEBUG 486 m_value.asRaw = reinterpret_cast<MediaConstraint*>(0xbbadbeef); 487 #endif 488 } 489 490 MediaConstraint& constraint() const { return *m_value.asRaw; } 491 MediaConstraint::DataType dataType() const { return constraint().dataType(); } 492 MediaConstraintType constraintType() const { return constraint().constraintType(); } 493 494 private: 495 explicit ConstraintHolder(const MediaConstraint& value) 496 { 497 switch (value.dataType()) { 498 case MediaConstraint::DataType::Integer: 499 m_value.asInteger = new IntConstraint(downcast<const IntConstraint>(value)); 500 break; 501 case MediaConstraint::DataType::Double: 502 m_value.asDouble = new DoubleConstraint(downcast<DoubleConstraint>(value)); 503 break; 504 case MediaConstraint::DataType::Boolean: 505 m_value.asBoolean = new BooleanConstraint(downcast<BooleanConstraint>(value)); 506 break; 507 case MediaConstraint::DataType::String: 508 m_value.asString = new StringConstraint(downcast<StringConstraint>(value)); 509 break; 510 case MediaConstraint::DataType::None: 511 ASSERT_NOT_REACHED(); 512 break; 513 } 514 } 515 516 union { 517 MediaConstraint* asRaw; 518 IntConstraint* asInteger; 519 DoubleConstraint* asDouble; 520 BooleanConstraint* asBoolean; 521 StringConstraint* asString; 522 } m_value; 523 }; 524 525 Vector<ConstraintHolder> m_variants; 526 #ifndef NDEBUG 527 int m_generation { 0 }; 528 #endif 424 529 }; 425 530 … … 438 543 } // namespace WebCore 439 544 545 #define SPECIALIZE_TYPE_TRAITS_MEDIACONSTRAINT(ConstraintType, predicate) \ 546 SPECIALIZE_TYPE_TRAITS_BEGIN(WebCore::ConstraintType) \ 547 static bool isType(const WebCore::MediaConstraint& constraint) { return constraint.predicate; } \ 548 SPECIALIZE_TYPE_TRAITS_END() 549 550 SPECIALIZE_TYPE_TRAITS_MEDIACONSTRAINT(IntConstraint, isInt()) 551 SPECIALIZE_TYPE_TRAITS_MEDIACONSTRAINT(DoubleConstraint, isDouble()) 552 SPECIALIZE_TYPE_TRAITS_MEDIACONSTRAINT(StringConstraint, isString()) 553 SPECIALIZE_TYPE_TRAITS_MEDIACONSTRAINT(BooleanConstraint, isBoolean()) 554 440 555 #endif // ENABLE(MEDIA_STREAM) 441 556 -
trunk/Source/WebCore/platform/mediastream/RealtimeMediaSource.cpp
r205574 r206445 151 151 } 152 152 153 #if 1 153 154 double RealtimeMediaSource::fitnessDistance(const MediaConstraint& constraint) 154 155 { 155 156 RealtimeMediaSourceCapabilities& capabilities = *this->capabilities(); 156 157 157 switch (constraint. type()) {158 switch (constraint.constraintType()) { 158 159 case MediaConstraintType::Width: { 160 ASSERT(constraint.isInt()); 159 161 if (!capabilities.supportsWidth()) 160 162 return 0; 161 163 162 164 auto range = capabilities.width(); 163 return constraint.fitnessDistance(range.rangeMin().asInt, range.rangeMax().asInt);165 return downcast<IntConstraint>(constraint).fitnessDistance(range.rangeMin().asInt, range.rangeMax().asInt); 164 166 break; 165 167 } 166 168 167 169 case MediaConstraintType::Height: { 170 ASSERT(constraint.isInt()); 168 171 if (!capabilities.supportsHeight()) 169 172 return 0; 170 173 171 174 auto range = capabilities.height(); 172 return constraint.fitnessDistance(range.rangeMin().asInt, range.rangeMax().asInt);175 return downcast<IntConstraint>(constraint).fitnessDistance(range.rangeMin().asInt, range.rangeMax().asInt); 173 176 break; 174 177 } 175 178 176 179 case MediaConstraintType::FrameRate: { 180 ASSERT(constraint.isDouble()); 177 181 if (!capabilities.supportsFrameRate()) 178 182 return 0; 179 183 180 184 auto range = capabilities.frameRate(); 181 return constraint.fitnessDistance(range.rangeMin().asDouble, range.rangeMax().asDouble);185 return downcast<DoubleConstraint>(constraint).fitnessDistance(range.rangeMin().asDouble, range.rangeMax().asDouble); 182 186 break; 183 187 } 184 188 185 189 case MediaConstraintType::AspectRatio: { 190 ASSERT(constraint.isDouble()); 186 191 if (!capabilities.supportsAspectRatio()) 187 192 return 0; 188 193 189 194 auto range = capabilities.aspectRatio(); 190 return constraint.fitnessDistance(range.rangeMin().asDouble, range.rangeMax().asDouble);195 return downcast<DoubleConstraint>(constraint).fitnessDistance(range.rangeMin().asDouble, range.rangeMax().asDouble); 191 196 break; 192 197 } 193 198 194 199 case MediaConstraintType::Volume: { 200 ASSERT(constraint.isDouble()); 195 201 if (!capabilities.supportsVolume()) 196 202 return 0; 197 203 198 204 auto range = capabilities.volume(); 199 return constraint.fitnessDistance(range.rangeMin().asDouble, range.rangeMax().asDouble);205 return downcast<DoubleConstraint>(constraint).fitnessDistance(range.rangeMin().asDouble, range.rangeMax().asDouble); 200 206 break; 201 207 } 202 208 203 209 case MediaConstraintType::SampleRate: { 210 ASSERT(constraint.isInt()); 204 211 if (!capabilities.supportsSampleRate()) 205 212 return 0; 206 213 207 214 auto range = capabilities.sampleRate(); 208 return constraint.fitnessDistance(range.rangeMin().asDouble, range.rangeMax().asDouble);215 return downcast<IntConstraint>(constraint).fitnessDistance(range.rangeMin().asInt, range.rangeMax().asInt); 209 216 break; 210 217 } 211 218 212 219 case MediaConstraintType::SampleSize: { 220 ASSERT(constraint.isInt()); 213 221 if (!capabilities.supportsSampleSize()) 214 222 return 0; 215 223 216 224 auto range = capabilities.sampleSize(); 217 return constraint.fitnessDistance(range.rangeMin().asDouble, range.rangeMax().asDouble);225 return downcast<IntConstraint>(constraint).fitnessDistance(range.rangeMin().asInt, range.rangeMax().asInt); 218 226 break; 219 227 } 220 228 221 229 case MediaConstraintType::FacingMode: { 230 ASSERT(constraint.isString()); 222 231 if (!capabilities.supportsFacingMode()) 223 232 return 0; … … 228 237 for (auto& mode : modes) 229 238 supportedModes.append(RealtimeMediaSourceSettings::facingMode(mode)); 230 return constraint.fitnessDistance(supportedModes);239 return downcast<StringConstraint>(constraint).fitnessDistance(supportedModes); 231 240 break; 232 241 } 233 242 234 243 case MediaConstraintType::EchoCancellation: { 244 ASSERT(constraint.isBoolean()); 235 245 if (!capabilities.supportsEchoCancellation()) 236 246 return 0; 237 247 238 248 bool echoCancellationReadWrite = capabilities.echoCancellation() == RealtimeMediaSourceCapabilities::EchoCancellation::ReadWrite; 239 return constraint.fitnessDistance(echoCancellationReadWrite);249 return downcast<BooleanConstraint>(constraint).fitnessDistance(echoCancellationReadWrite); 240 250 break; 241 251 } 242 252 243 253 case MediaConstraintType::DeviceId: { 254 ASSERT(constraint.isString()); 244 255 if (!capabilities.supportsDeviceId()) 245 256 return 0; 246 257 247 return constraint.fitnessDistance(m_id);258 return downcast<StringConstraint>(constraint).fitnessDistance(m_id); 248 259 break; 249 260 } 250 261 251 262 case MediaConstraintType::GroupId: { 263 ASSERT(constraint.isString()); 252 264 if (!capabilities.supportsDeviceId()) 253 265 return 0; 254 266 255 return constraint.fitnessDistance(settings().groupId());267 return downcast<StringConstraint>(constraint).fitnessDistance(settings().groupId()); 256 268 break; 257 269 } … … 264 276 return 0; 265 277 } 278 #endif 266 279 267 280 template <typename ValueType> 268 static void applyNumericConstraint(const MediaConstraint& constraint, ValueType current, ValueType capabilityMin, ValueType capabilityMax, RealtimeMediaSource* source, void (RealtimeMediaSource::*function)(ValueType))281 static void applyNumericConstraint(const NumericConstraint<ValueType>& constraint, ValueType current, ValueType capabilityMin, ValueType capabilityMax, RealtimeMediaSource* source, void (RealtimeMediaSource::*applier)(ValueType)) 269 282 { 270 283 ValueType value; … … 274 287 if (constraint.getExact(value)) { 275 288 ASSERT(constraint.validForRange(capabilityMin, capabilityMax)); 276 (source->* function)(value);289 (source->*applier)(value); 277 290 return; 278 291 } … … 303 316 304 317 if (value != current) 305 (source->* function)(value);318 (source->*applier)(value); 306 319 } 307 320 … … 309 322 { 310 323 RealtimeMediaSourceCapabilities& capabilities = *this->capabilities(); 311 switch (constraint. type()) {324 switch (constraint.constraintType()) { 312 325 case MediaConstraintType::Width: { 326 ASSERT(constraint.isInt()); 313 327 if (!capabilities.supportsWidth()) 314 328 return; 315 329 316 330 auto range = capabilities.width(); 317 applyNumericConstraint( constraint, size().width(), range.rangeMin().asInt, range.rangeMax().asInt, this, &RealtimeMediaSource::setWidth);331 applyNumericConstraint(downcast<IntConstraint>(constraint), size().width(), range.rangeMin().asInt, range.rangeMax().asInt, this, &RealtimeMediaSource::setWidth); 318 332 break; 319 333 } 320 334 321 335 case MediaConstraintType::Height: { 336 ASSERT(constraint.isInt()); 322 337 if (!capabilities.supportsHeight()) 323 338 return; 324 339 325 340 auto range = capabilities.height(); 326 applyNumericConstraint( constraint, size().height(), range.rangeMin().asInt, range.rangeMax().asInt, this, &RealtimeMediaSource::setHeight);341 applyNumericConstraint(downcast<IntConstraint>(constraint), size().height(), range.rangeMin().asInt, range.rangeMax().asInt, this, &RealtimeMediaSource::setHeight); 327 342 break; 328 343 } 329 344 330 345 case MediaConstraintType::FrameRate: { 346 ASSERT(constraint.isDouble()); 331 347 if (!capabilities.supportsFrameRate()) 332 348 return; 333 349 334 350 auto range = capabilities.frameRate(); 335 applyNumericConstraint( constraint, frameRate(), range.rangeMin().asDouble, range.rangeMax().asDouble, this, &RealtimeMediaSource::setFrameRate);351 applyNumericConstraint(downcast<DoubleConstraint>(constraint), frameRate(), range.rangeMin().asDouble, range.rangeMax().asDouble, this, &RealtimeMediaSource::setFrameRate); 336 352 break; 337 353 } 338 354 339 355 case MediaConstraintType::AspectRatio: { 356 ASSERT(constraint.isDouble()); 340 357 if (!capabilities.supportsAspectRatio()) 341 358 return; 342 359 343 360 auto range = capabilities.aspectRatio(); 344 applyNumericConstraint( constraint, aspectRatio(), range.rangeMin().asDouble, range.rangeMax().asDouble, this, &RealtimeMediaSource::setAspectRatio);361 applyNumericConstraint(downcast<DoubleConstraint>(constraint), aspectRatio(), range.rangeMin().asDouble, range.rangeMax().asDouble, this, &RealtimeMediaSource::setAspectRatio); 345 362 break; 346 363 } 347 364 348 365 case MediaConstraintType::Volume: { 366 ASSERT(constraint.isDouble()); 349 367 if (!capabilities.supportsVolume()) 350 368 return; 351 369 352 370 auto range = capabilities.volume(); 353 applyNumericConstraint( constraint, volume(), range.rangeMin().asDouble, range.rangeMax().asDouble, this, &RealtimeMediaSource::setVolume);371 applyNumericConstraint(downcast<DoubleConstraint>(constraint), volume(), range.rangeMin().asDouble, range.rangeMax().asDouble, this, &RealtimeMediaSource::setVolume); 354 372 break; 355 373 } 356 374 357 375 case MediaConstraintType::SampleRate: { 376 ASSERT(constraint.isInt()); 358 377 if (!capabilities.supportsSampleRate()) 359 378 return; 360 379 361 380 auto range = capabilities.sampleRate(); 362 applyNumericConstraint( constraint, sampleRate(), range.rangeMin().asDouble, range.rangeMax().asDouble, this, &RealtimeMediaSource::setSampleRate);381 applyNumericConstraint(downcast<IntConstraint>(constraint), sampleRate(), range.rangeMin().asInt, range.rangeMax().asInt, this, &RealtimeMediaSource::setSampleRate); 363 382 break; 364 383 } 365 384 366 385 case MediaConstraintType::SampleSize: { 386 ASSERT(constraint.isInt()); 367 387 if (!capabilities.supportsSampleSize()) 368 388 return; 369 389 370 390 auto range = capabilities.sampleSize(); 371 applyNumericConstraint(constraint, sampleSize(), range.rangeMin().asDouble, range.rangeMax().asDouble, this, &RealtimeMediaSource::setSampleSize); 372 break; 373 } 374 375 case MediaConstraintType::EchoCancellation: 391 applyNumericConstraint(downcast<IntConstraint>(constraint), sampleSize(), range.rangeMin().asInt, range.rangeMax().asInt, this, &RealtimeMediaSource::setSampleSize); 392 break; 393 } 394 395 case MediaConstraintType::EchoCancellation: { 396 ASSERT(constraint.isBoolean()); 376 397 if (!capabilities.supportsEchoCancellation()) 377 398 return; 378 399 379 400 bool setting; 380 if (constraint.getExact(setting) || constraint.getIdeal(setting)) 401 const BooleanConstraint& boolConstraint = downcast<BooleanConstraint>(constraint); 402 if (boolConstraint.getExact(setting) || boolConstraint.getIdeal(setting)) 381 403 setEchoCancellation(setting); 382 404 break; 405 } 383 406 384 407 case MediaConstraintType::FacingMode: { 408 ASSERT(constraint.isString()); 385 409 if (!capabilities.supportsFacingMode()) 386 410 return; 387 411 388 412 auto& supportedModes = capabilities.facingMode(); 389 std::function<bool(MediaConstraint::ConstraintType, const String&)> filter = [supportedModes](MediaConstraint::ConstraintType,const String& modeString) {413 auto filter = [supportedModes](const String& modeString) { 390 414 auto mode = RealtimeMediaSourceSettings::videoFacingModeEnum(modeString); 391 415 for (auto& supportedMode : supportedModes) { … … 396 420 }; 397 421 398 auto modeString = constraint.find(filter);422 auto modeString = downcast<StringConstraint>(constraint).find(filter); 399 423 if (!modeString.isEmpty()) 400 424 setFacingMode(RealtimeMediaSourceSettings::videoFacingModeEnum(modeString)); … … 404 428 case MediaConstraintType::DeviceId: 405 429 case MediaConstraintType::GroupId: 430 ASSERT(constraint.isString()); 406 431 // There is nothing to do here, neither can be changed. 407 432 break; … … 432 457 // properties as ideal values. Let candidates be the set of settings dictionaries for which the fitness 433 458 // distance is finite. 434 auto& mandatoryConstraints = constraints.mandatoryConstraints(); 435 f or (auto& nameConstraintPair : mandatoryConstraints) {436 const auto& constraint = nameConstraintPair.value;437 if (fitnessDistance( *constraint) == std::numeric_limits<double>::infinity()) {438 failedConstraint = constraint ->name();439 return false;459 460 failedConstraint = emptyString(); 461 constraints.mandatoryConstraints().filter([&](const MediaConstraint& constraint) { 462 if (fitnessDistance(constraint) == std::numeric_limits<double>::infinity()) { 463 failedConstraint = constraint.name(); 464 return true; 440 465 } 441 466 442 candidates.set(*constraint); 443 } 467 candidates.set(constraint); 468 return false; 469 }); 470 471 if (!failedConstraint.isEmpty()) 472 return false; 444 473 445 474 // 4. If candidates is empty, return undefined as the result of the SelectSettings() algorithm. … … 454 483 Vector<std::pair<double, MediaTrackConstraintSetMap>> supportedConstraints; 455 484 double minimumDistance = std::numeric_limits<double>::infinity(); 485 456 486 for (const auto& advancedConstraint : constraints.advancedConstraints()) { 457 487 double constraintDistance = 0; 458 488 bool supported = false; 459 for (auto& nameConstraintPair : advancedConstraint) { 460 double distance = fitnessDistance(*nameConstraintPair.value); 489 490 advancedConstraint.forEach([&](const MediaConstraint& constraint) { 491 double distance = fitnessDistance(constraint); 461 492 constraintDistance += distance; 462 493 if (distance != std::numeric_limits<double>::infinity()) 463 494 supported = true; 464 } 495 }); 465 496 466 497 if (constraintDistance < minimumDistance) … … 477 508 // The UA should use the one with the smallest fitness distance, as calculated in step 3. 478 509 if (minimumDistance != std::numeric_limits<double>::infinity()) { 479 supportedConstraints.removeAllMatching( [&](std::pair<double, MediaTrackConstraintSetMap> pair) -> bool {510 supportedConstraints.removeAllMatching([&](std::pair<double, MediaTrackConstraintSetMap> pair) -> bool { 480 511 return pair.first > minimumDistance; 481 512 }); … … 483 514 if (!supportedConstraints.isEmpty()) { 484 515 auto& advancedConstraint = supportedConstraints[0].second; 485 for (auto& nameConstraintPair : advancedConstraint) 486 candidates.merge(*nameConstraintPair.value); 516 advancedConstraint.forEach([&](const MediaConstraint& constraint) { 517 candidates.merge(constraint); 518 }); 487 519 } 488 520 } … … 491 523 } 492 524 493 494 525 void RealtimeMediaSource::applyConstraints(const MediaConstraints& constraints, SuccessHandler successHandler, FailureHandler failureHandler) 495 526 { … … 497 528 498 529 FlattenedConstraint candidates; 499 500 530 String failedConstraint; 501 531 if (!selectSettings(constraints, candidates, failedConstraint)) { … … 504 534 } 505 535 506 for (auto constraint : candidates)507 applyConstraint( *constraint);536 for (auto& variant : candidates) 537 applyConstraint(variant); 508 538 509 539 successHandler(); … … 579 609 } 580 610 581 void RealtimeMediaSource::setSampleRate( doublerate)611 void RealtimeMediaSource::setSampleRate(int rate) 582 612 { 583 613 if (m_sampleRate == rate || !applySampleRate(rate)) … … 588 618 } 589 619 590 void RealtimeMediaSource::setSampleSize( doublesize)620 void RealtimeMediaSource::setSampleSize(int size) 591 621 { 592 622 if (m_sampleSize == size || !applySampleSize(size)) -
trunk/Source/WebCore/platform/mediastream/RealtimeMediaSource.h
r205574 r206445 149 149 virtual bool applyVolume(double) { return false; } 150 150 151 doublesampleRate() const { return m_sampleRate; }152 void setSampleRate( double);153 virtual bool applySampleRate( double) { return false; }154 155 doublesampleSize() const { return m_sampleSize; }156 void setSampleSize( double);157 virtual bool applySampleSize( double) { return false; }151 int sampleRate() const { return m_sampleRate; } 152 void setSampleRate(int); 153 virtual bool applySampleRate(int) { return false; } 154 155 int sampleSize() const { return m_sampleSize; } 156 void setSampleSize(int); 157 virtual bool applySampleSize(int) { return false; } 158 158 159 159 bool echoCancellation() const { return m_echoCancellation; } … … 171 171 WeakPtr<RealtimeMediaSource> createWeakPtr() { return m_weakPtrFactory.createWeakPtr(); } 172 172 173 bool supportsConstraints(const MediaTrackConstraintSetMap&);174 173 bool selectSettings(const MediaConstraints&, FlattenedConstraint&, String&); 175 174 double fitnessDistance(const MediaConstraint&); -
trunk/Source/WebCore/platform/mediastream/mac/AVCaptureDeviceManager.mm
r205929 r206445 268 268 { 269 269 const RealtimeMediaSourceSupportedConstraints& supportedConstraints = RealtimeMediaSourceCenter::singleton().supportedConstraints(); 270 MediaConstraintType constraintType = constraint. type();270 MediaConstraintType constraintType = constraint.constraintType(); 271 271 if (!supportedConstraints.supportsConstraint(constraintType)) 272 272 return false; … … 280 280 // FIXME: https://bugs.webkit.org/show_bug.cgi?id=160578. Support min, max constraints. 281 281 int exact; 282 if (! constraint.getExact(exact))282 if (!downcast<const IntConstraint>(constraint).getExact(exact)) 283 283 return false; 284 284 … … 289 289 // FIXME: https://bugs.webkit.org/show_bug.cgi?id=160578. Support min, max constraints. 290 290 int exact; 291 if (! constraint.getExact(exact))291 if (!downcast<const IntConstraint>(constraint).getExact(exact)) 292 292 return false; 293 293 -
trunk/Source/WebCore/platform/mock/MediaConstraintsMock.cpp
r204595 r206445 44 44 45 45 int min = floor; 46 if ( constraint.getMin(min) && min > ceiling)46 if (downcast<const IntConstraint>(constraint).getMin(min) && min > ceiling) 47 47 return false; 48 48 49 49 int max = ceiling; 50 if ( constraint.getMax(max) && max < min)50 if (downcast<const IntConstraint>(constraint).getMax(max) && max < min) 51 51 return false; 52 52 53 53 int exact; 54 if ( constraint.getExact(exact) && (exact < min || exact > max))54 if (downcast<const IntConstraint>(constraint).getExact(exact) && (exact < min || exact > max)) 55 55 return false; 56 56 … … 64 64 65 65 double min = floor; 66 if ( constraint.getMin(min) && min > ceiling)66 if (downcast<const DoubleConstraint>(constraint).getMin(min) && min > ceiling) 67 67 return false; 68 68 69 69 double max = ceiling; 70 if ( constraint.getMax(max) && max < min)70 if (downcast<const DoubleConstraint>(constraint).getMax(max) && max < min) 71 71 return false; 72 72 73 73 double exact; 74 if ( constraint.getExact(exact) && (exact < min || exact > max))74 if (downcast<const DoubleConstraint>(constraint).getExact(exact) && (exact < min || exact > max)) 75 75 return false; 76 76 … … 81 81 { 82 82 bool exact; 83 if ( constraint.getExact(exact))83 if (downcast<const BooleanConstraint>(constraint).getExact(exact)) 84 84 return exact; 85 85 … … 90 90 { 91 91 Vector<String> exact; 92 if ( constraint.getExact(exact)) {92 if (downcast<const StringConstraint>(constraint).getExact(exact)) { 93 93 for (auto& constraintValue : exact) { 94 94 if (constraintValue.find("invalid") != notFound) … … 102 102 static bool isSatisfiable(RealtimeMediaSource::Type type, const MediaConstraint& constraint) 103 103 { 104 MediaConstraintType constraintType = constraint. type();104 MediaConstraintType constraintType = constraint.constraintType(); 105 105 106 106 if (type == RealtimeMediaSource::Audio) { … … 125 125 } 126 126 127 const String &MediaConstraintsMock::verifyConstraints(RealtimeMediaSource::Type type, const MediaConstraints& constraints)127 const String MediaConstraintsMock::verifyConstraints(RealtimeMediaSource::Type type, const MediaConstraints& constraints) 128 128 { 129 auto& mandatoryConstraints = constraints.mandatoryConstraints(); 130 for (auto& nameConstraintPair : mandatoryConstraints) { 131 if (!isSatisfiable(type, *nameConstraintPair.value)) 132 return nameConstraintPair.key; 133 } 129 String invalidConstraint = emptyString(); 130 constraints.mandatoryConstraints().filter([&](const MediaConstraint& constraint) { 131 if (!isSatisfiable(type, constraint)) { 132 invalidConstraint = constraint.name(); 133 return true; 134 } 134 135 135 return emptyString(); 136 return false; 137 }); 138 139 return invalidConstraint; 140 136 141 } 137 142 -
trunk/Source/WebCore/platform/mock/MediaConstraintsMock.h
r204516 r206445 40 40 class MediaConstraintsMock { 41 41 public: 42 static const String &verifyConstraints(RealtimeMediaSource::Type, const MediaConstraints&);42 static const String verifyConstraints(RealtimeMediaSource::Type, const MediaConstraints&); 43 43 }; 44 44 -
trunk/Source/WebCore/platform/mock/MockRealtimeAudioSource.h
r205348 r206445 54 54 55 55 bool applyVolume(double) override { return true; } 56 bool applySampleRate( double) override { return true; }57 bool applySampleSize( double) override { return true; }56 bool applySampleRate(int) override { return true; } 57 bool applySampleSize(int) override { return true; } 58 58 bool applyEchoCancellation(bool) override { return true; } 59 59 -
trunk/Source/WebCore/platform/mock/MockRealtimeMediaSourceCenter.cpp
r205929 r206445 110 110 111 111 if (audioConstraints.isValid()) { 112 const String &invalidQuery = MediaConstraintsMock::verifyConstraints(RealtimeMediaSource::Audio, audioConstraints);112 const String invalidQuery = MediaConstraintsMock::verifyConstraints(RealtimeMediaSource::Audio, audioConstraints); 113 113 if (!invalidQuery.isEmpty()) { 114 114 client->failedToCreateStreamWithConstraintsError(invalidQuery); … … 121 121 122 122 if (videoConstraints.isValid()) { 123 const String &invalidQuery = MediaConstraintsMock::verifyConstraints(RealtimeMediaSource::Video, videoConstraints);123 const String invalidQuery = MediaConstraintsMock::verifyConstraints(RealtimeMediaSource::Video, videoConstraints); 124 124 if (!invalidQuery.isEmpty()) { 125 125 client->failedToCreateStreamWithConstraintsError(invalidQuery);
Note:
See TracChangeset
for help on using the changeset viewer.