Home | History | Annotate | Download | only in css
      1 /*
      2  * Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies)
      3  *
      4  *  This library is free software; you can redistribute it and/or
      5  *  modify it under the terms of the GNU Library General Public
      6  *  License as published by the Free Software Foundation; either
      7  *  version 2 of the License, or (at your option) any later version.
      8  *
      9  *  This library is distributed in the hope that it will be useful,
     10  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
     11  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
     12  *  Library General Public License for more details.
     13  *
     14  *  You should have received a copy of the GNU Library General Public License
     15  *  along with this library; see the file COPYING.LIB.  If not, write to
     16  *  the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
     17  *  Boston, MA 02110-1301, USA.
     18  */
     19 
     20 #include "config.h"
     21 #include "core/css/MediaQueryList.h"
     22 
     23 #include "core/css/MediaList.h"
     24 #include "core/css/MediaQueryEvaluator.h"
     25 #include "core/css/MediaQueryListListener.h"
     26 #include "core/css/MediaQueryMatcher.h"
     27 #include "core/dom/Document.h"
     28 
     29 namespace blink {
     30 
     31 PassRefPtrWillBeRawPtr<MediaQueryList> MediaQueryList::create(ExecutionContext* context, PassRefPtrWillBeRawPtr<MediaQueryMatcher> matcher, PassRefPtrWillBeRawPtr<MediaQuerySet> media)
     32 {
     33     RefPtrWillBeRawPtr<MediaQueryList> list = adoptRefWillBeNoop(new MediaQueryList(context, matcher, media));
     34     list->suspendIfNeeded();
     35     return list.release();
     36 }
     37 
     38 MediaQueryList::MediaQueryList(ExecutionContext* context, PassRefPtrWillBeRawPtr<MediaQueryMatcher> matcher, PassRefPtrWillBeRawPtr<MediaQuerySet> media)
     39     : ActiveDOMObject(context)
     40     , m_matcher(matcher)
     41     , m_media(media)
     42     , m_matchesDirty(true)
     43     , m_matches(false)
     44 {
     45     m_matcher->addMediaQueryList(this);
     46     updateMatches();
     47 }
     48 
     49 MediaQueryList::~MediaQueryList()
     50 {
     51 #if !ENABLE(OILPAN)
     52     m_matcher->removeMediaQueryList(this);
     53 #endif
     54 }
     55 
     56 String MediaQueryList::media() const
     57 {
     58     return m_media->mediaText();
     59 }
     60 
     61 void MediaQueryList::addDeprecatedListener(PassRefPtr<EventListener> listener)
     62 {
     63     addEventListener(EventTypeNames::change, listener, false);
     64 }
     65 
     66 void MediaQueryList::removeDeprecatedListener(PassRefPtr<EventListener> listener)
     67 {
     68     removeEventListener(EventTypeNames::change, listener, false);
     69 }
     70 
     71 void MediaQueryList::addListener(PassRefPtrWillBeRawPtr<MediaQueryListListener> listener)
     72 {
     73     if (!listener)
     74         return;
     75 
     76     m_listeners.add(listener);
     77 }
     78 
     79 void MediaQueryList::removeListener(PassRefPtrWillBeRawPtr<MediaQueryListListener> listener)
     80 {
     81     if (!listener)
     82         return;
     83 
     84     RefPtrWillBeRawPtr<MediaQueryList> protect(this);
     85     m_listeners.remove(listener);
     86 }
     87 
     88 bool MediaQueryList::hasPendingActivity() const
     89 {
     90     return m_listeners.size() || hasEventListeners(EventTypeNames::change);
     91 }
     92 
     93 void MediaQueryList::stop()
     94 {
     95     // m_listeners.clear() can drop the last ref to this MediaQueryList.
     96     RefPtrWillBeRawPtr<MediaQueryList> protect(this);
     97     m_listeners.clear();
     98     removeAllEventListeners();
     99 }
    100 
    101 bool MediaQueryList::mediaFeaturesChanged(WillBeHeapVector<RefPtrWillBeMember<MediaQueryListListener> >* listenersToNotify)
    102 {
    103     m_matchesDirty = true;
    104     if (!updateMatches())
    105         return false;
    106     for (ListenerList::const_iterator it = m_listeners.begin(), end = m_listeners.end(); it != end; ++it) {
    107         listenersToNotify->append(*it);
    108     }
    109     return hasEventListeners(EventTypeNames::change);
    110 }
    111 
    112 bool MediaQueryList::updateMatches()
    113 {
    114     m_matchesDirty = false;
    115     if (m_matches != m_matcher->evaluate(m_media.get())) {
    116         m_matches = !m_matches;
    117         return true;
    118     }
    119     return false;
    120 }
    121 
    122 bool MediaQueryList::matches()
    123 {
    124     updateMatches();
    125     return m_matches;
    126 }
    127 
    128 void MediaQueryList::trace(Visitor* visitor)
    129 {
    130 #if ENABLE(OILPAN)
    131     visitor->trace(m_matcher);
    132     visitor->trace(m_media);
    133     visitor->trace(m_listeners);
    134 #endif
    135     EventTargetWithInlineData::trace(visitor);
    136 }
    137 
    138 const AtomicString& MediaQueryList::interfaceName() const
    139 {
    140     return EventTargetNames::MediaQueryList;
    141 }
    142 
    143 ExecutionContext* MediaQueryList::executionContext() const
    144 {
    145     return ActiveDOMObject::executionContext();
    146 }
    147 
    148 }
    149