Commit f12b93a3 authored by apavlov@chromium.org's avatar apavlov@chromium.org

DevTools: Decouple CSS model from UI entities

CSSPresentationModel has been introduced in order to
- manage source mappings,
- store live locations,
- perform the rawLocationToUILocation conversions.

R=pfeldman, vsevik

Review URL: https://codereview.chromium.org/297923002

git-svn-id: svn://svn.chromium.org/blink/trunk@179012 bbb929c8-8fbe-4397-9dbb-9b2b20218538
parent 0e0f1297
......@@ -25,9 +25,9 @@ function test()
function step1()
{
InspectorTest.addSniffer(WebInspector.CSSStyleSheetHeader.prototype, "pushSourceMapping", sourceMappingSniffer, true);
InspectorTest.addSniffer(WebInspector.CSSWorkspaceBinding.prototype, "pushSourceMapping", sourceMappingSniffer, true);
function sourceMappingSniffer(sourceMapping)
function sourceMappingSniffer(header, sourceMapping)
{
if (sourceMapping instanceof WebInspector.SASSSourceMapping) {
WebInspector.inspectorView.showPanel("elements");
......
......@@ -65,7 +65,7 @@ function test()
var target = WebInspector.targetManager.mainTarget();
cssModel = new WebInspector.CSSStyleModel(target, InspectorTest.testWorkspace);
target.cssModel = cssModel;
new WebInspector.CSSStyleSheetMapping(cssModel, InspectorTest.testWorkspace, InspectorTest.testNetworkWorkspaceBinding);
new WebInspector.CSSWorkspaceBinding.TargetInfo(target, InspectorTest.testWorkspace, InspectorTest.testNetworkWorkspaceBinding);
var resourcesURL = WebInspector.ParsedURL.completeURL(WebInspector.resourceTreeModel.inspectedPageURL(), "resources/");
var namePrefix = "update-locations-on-filesystem-scss-load."
......
......@@ -12,9 +12,9 @@ function test()
var finalMappedLocation;
InspectorTest.createWorkspace();
var target = WebInspector.targetManager.mainTarget();
var cssModel = new WebInspector.CSSStyleModel(target, InspectorTest.testWorkspace);
var cssModel = new WebInspector.CSSStyleModel(target);
target.cssModel = cssModel;
var mapping = new WebInspector.CSSStyleSheetMapping(cssModel, InspectorTest.testWorkspace, InspectorTest.testNetworkWorkspaceBinding);
new WebInspector.CSSWorkspaceBinding.TargetInfo(target, InspectorTest.testWorkspace, InspectorTest.testNetworkWorkspaceBinding);
InspectorTest.waitForWorkspaceUISourceCodeAddedEvent(cssUISourceCodeAdded);
const styleSheetURL = "http://localhost:8000/inspector/resources/example.css";
......@@ -22,7 +22,7 @@ function test()
const styleSheetId = 1;
InspectorTest.addMockUISourceCodeToWorkspace(styleSheetURL, WebInspector.resourceTypes.Stylesheet, "");
InspectorTest.addSniffer(WebInspector.CSSStyleSheetHeader.prototype, "updateLocations", locationsUpdated, true);
InspectorTest.addSniffer(WebInspector.CSSWorkspaceBinding.prototype, "updateLocations", locationsUpdated, true);
cssModel._styleSheetAdded(createMockStyleSheetHeader(styleSheetURL, sourceMapURL));
function locationsUpdated()
......
......@@ -90,7 +90,6 @@
'front_end/sdk/CSSMetadata.js',
'front_end/sdk/CSSParser.js',
'front_end/sdk/CSSStyleModel.js',
'front_end/sdk/CSSStyleSheetMapping.js',
'front_end/sdk/CSSWorkspaceBinding.js',
'front_end/sdk/BreakpointManager.js',
'front_end/sdk/DOMModel.js',
......
......@@ -151,7 +151,6 @@ THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
<script type="text/javascript" src="sdk/ResourceScriptMapping.js"></script>
<script type="text/javascript" src="sdk/CompilerScriptMapping.js"></script>
<script type="text/javascript" src="sdk/LiveEditSupport.js"></script>
<script type="text/javascript" src="sdk/CSSStyleSheetMapping.js"></script>
<script type="text/javascript" src="sdk/SASSSourceMapping.js"></script>
<script type="text/javascript" src="sdk/DOMModel.js"></script>
<script type="text/javascript" src="ui/ForwardedInputEventHandler.js"></script>
......
......@@ -359,7 +359,6 @@ WebInspector.Main.prototype = {
WebInspector.openAnchorLocationRegistry.registerHandler(autoselectPanel, function() { return false; });
WebInspector.Linkifier.setLinkHandler(new WebInspector.HandlerRegistry.LinkHandler());
new WebInspector.WorkspaceController(WebInspector.workspace);
new WebInspector.CSSStyleSheetMapping(WebInspector.cssModel, WebInspector.workspace, WebInspector.networkWorkspaceBinding);
new WebInspector.RenderingOptions();
new WebInspector.Main.PauseListener();
new WebInspector.Main.InspectedNodeRevealer();
......
......@@ -595,138 +595,9 @@ WebInspector.CSSStyleModel.prototype = {
this.dispatchEventToListeners(WebInspector.CSSStyleModel.Events.StyleSheetRemoved, headers[i]);
},
updateLocations: function()
{
var headers = this._styleSheetIdToHeader.values();
for (var i = 0; i < headers.length; ++i)
headers[i].updateLocations();
},
/**
* @param {?CSSAgent.StyleSheetId} styleSheetId
* @param {!WebInspector.CSSLocation} rawLocation
* @param {function(!WebInspector.UILocation):(boolean|undefined)} updateDelegate
* @return {?WebInspector.LiveLocation}
*/
createLiveLocation: function(styleSheetId, rawLocation, updateDelegate)
{
if (!rawLocation)
return null;
var header = styleSheetId ? this.styleSheetHeaderForId(styleSheetId) : null;
return new WebInspector.CSSStyleModel.LiveLocation(this, header, rawLocation, updateDelegate);
},
/**
* @param {!WebInspector.CSSLocation} rawLocation
* @return {?WebInspector.UILocation}
*/
rawLocationToUILocation: function(rawLocation)
{
var frameIdToSheetIds = this._styleSheetIdsForURL.get(rawLocation.url);
if (!frameIdToSheetIds)
return null;
var styleSheetIds = [];
for (var frameId in frameIdToSheetIds)
styleSheetIds = styleSheetIds.concat(frameIdToSheetIds[frameId]);
var uiLocation;
for (var i = 0; !uiLocation && i < styleSheetIds.length; ++i) {
var header = this.styleSheetHeaderForId(styleSheetIds[i]);
console.assert(header);
uiLocation = header.rawLocationToUILocation(rawLocation.lineNumber, rawLocation.columnNumber);
}
return uiLocation || null;
},
__proto__: WebInspector.SDKModel.prototype
}
/**
* @constructor
* @extends {WebInspector.LiveLocation}
* @param {!WebInspector.CSSStyleModel} model
* @param {?WebInspector.CSSStyleSheetHeader} header
* @param {!WebInspector.CSSLocation} rawLocation
* @param {function(!WebInspector.UILocation):(boolean|undefined)} updateDelegate
*/
WebInspector.CSSStyleModel.LiveLocation = function(model, header, rawLocation, updateDelegate)
{
WebInspector.LiveLocation.call(this, rawLocation, updateDelegate);
this._model = model;
if (!header)
this._clearStyleSheet();
else
this._setStyleSheet(header);
}
WebInspector.CSSStyleModel.LiveLocation.prototype = {
/**
* @param {!WebInspector.Event} event
*/
_styleSheetAdded: function(event)
{
console.assert(!this._header);
var header = /** @type {!WebInspector.CSSStyleSheetHeader} */ (event.data);
if (header.sourceURL && header.sourceURL === this.rawLocation().url)
this._setStyleSheet(header);
},
/**
* @param {!WebInspector.Event} event
*/
_styleSheetRemoved: function(event)
{
console.assert(this._header);
var header = /** @type {!WebInspector.CSSStyleSheetHeader} */ (event.data);
if (this._header !== header)
return;
this._header._removeLocation(this);
this._clearStyleSheet();
},
/**
* @param {!WebInspector.CSSStyleSheetHeader} header
*/
_setStyleSheet: function(header)
{
this._header = header;
this._header.addLiveLocation(this);
this._model.removeEventListener(WebInspector.CSSStyleModel.Events.StyleSheetAdded, this._styleSheetAdded, this);
this._model.addEventListener(WebInspector.CSSStyleModel.Events.StyleSheetRemoved, this._styleSheetRemoved, this);
},
_clearStyleSheet: function()
{
delete this._header;
this._model.removeEventListener(WebInspector.CSSStyleModel.Events.StyleSheetRemoved, this._styleSheetRemoved, this);
this._model.addEventListener(WebInspector.CSSStyleModel.Events.StyleSheetAdded, this._styleSheetAdded, this);
},
/**
* @return {?WebInspector.UILocation}
*/
uiLocation: function()
{
var cssLocation = /** @type WebInspector.CSSLocation */ (this.rawLocation());
if (this._header)
return this._header.rawLocationToUILocation(cssLocation.lineNumber, cssLocation.columnNumber);
var uiSourceCode = WebInspector.workspace.uiSourceCodeForURL(cssLocation.url);
if (!uiSourceCode)
return null;
return uiSourceCode.uiLocation(cssLocation.lineNumber, cssLocation.columnNumber);
},
dispose: function()
{
WebInspector.LiveLocation.prototype.dispose.call(this);
if (this._header)
this._header._removeLocation(this);
this._model.removeEventListener(WebInspector.CSSStyleModel.Events.StyleSheetAdded, this._styleSheetAdded, this);
this._model.removeEventListener(WebInspector.CSSStyleModel.Events.StyleSheetRemoved, this._styleSheetRemoved, this);
},
__proto__: WebInspector.LiveLocation.prototype
}
/**
* @constructor
* @implements {WebInspector.RawLocation}
......@@ -740,24 +611,13 @@ WebInspector.CSSStyleModel.LiveLocation.prototype = {
WebInspector.CSSLocation = function(target, styleSheetId, url, lineNumber, columnNumber)
{
WebInspector.SDKObject.call(this, target);
this._cssModel = target.cssModel;
this._styleSheetId = styleSheetId;
this.styleSheetId = styleSheetId;
this.url = url;
this.lineNumber = lineNumber;
this.columnNumber = columnNumber || 0;
}
WebInspector.CSSLocation.prototype = {
/**
* @param {function(!WebInspector.UILocation):(boolean|undefined)} updateDelegate
* @return {!WebInspector.LiveLocation}
*/
createLiveLocation: function(updateDelegate)
{
var header = this._styleSheetId ? this._cssModel.styleSheetHeaderForId(this._styleSheetId) : null;
return new WebInspector.CSSStyleModel.LiveLocation(this._cssModel, header, this, updateDelegate);
},
__proto__: WebInspector.SDKObject.prototype
}
......@@ -1063,7 +923,7 @@ WebInspector.CSSRule = function(cssModel, payload, matchingSelectors)
this.style.parentRule = this;
if (payload.media)
this.media = WebInspector.CSSMedia.parseMediaArrayPayload(cssModel, payload.media);
this._setRawLocationAndFrameId();
this._setFrameId();
}
/**
......@@ -1101,16 +961,12 @@ WebInspector.CSSRule.prototype = {
this.style.sourceStyleSheetEdited(styleSheetId, oldRange, newRange);
},
_setRawLocationAndFrameId: function()
_setFrameId: function()
{
if (!this.styleSheetId)
return;
var styleSheetHeader = this._cssModel.styleSheetHeaderForId(this.styleSheetId);
this.frameId = styleSheetHeader.frameId;
var url = styleSheetHeader.resourceURL();
if (!url)
return;
this.rawLocation = new WebInspector.CSSLocation(this._cssModel.target(), this.styleSheetId, url, this.lineNumberInSource(0), this.columnNumberInSource(0));
},
/**
......@@ -1151,6 +1007,17 @@ WebInspector.CSSRule.prototype = {
return styleSheetHeader.columnNumberInSource(selector.range.startLine, selector.range.startColumn);
},
/**
* @param {number} index
* @return {?WebInspector.CSSLocation}
*/
rawSelectorLocation: function(index)
{
var lineNumber = this.lineNumberInSource(index);
var columnNumber = this.columnNumberInSource(index);
return new WebInspector.CSSLocation(this._cssModel.target(), this.styleSheetId || null, this.resourceURL(), lineNumber, columnNumber);
},
get isUserAgent()
{
return this.origin === "user-agent";
......@@ -1522,28 +1389,10 @@ WebInspector.CSSMedia.prototype = {
*/
rawLocation: function()
{
if (!this.header() || typeof this.lineNumberInSource() === "undefined")
if (!this.header() || this.lineNumberInSource() === undefined)
return null;
var lineNumber = Number(this.lineNumberInSource());
return new WebInspector.CSSLocation(this._cssModel.target(), this.header().id, this.sourceURL, lineNumber, this.columnNumberInSource());
},
/**
* @return {?WebInspector.UILocation}
*/
uiLocation: function()
{
var styleSheetHeader = this.header();
var lineNumber = this.lineNumberInSource();
var columnNumber = this.columnNumberInSource();
if (typeof lineNumber !== "number")
return null;
if (styleSheetHeader)
return styleSheetHeader.rawLocationToUILocation(lineNumber, columnNumber);
var uiSourceCode = WebInspector.workspace.uiSourceCodeForURL(this.sourceURL);
if (!uiSourceCode)
return null;
return uiSourceCode.uiLocation(lineNumber, columnNumber);
}
}
......@@ -1567,66 +1416,23 @@ WebInspector.CSSStyleSheetHeader = function(cssModel, payload)
this.isInline = payload.isInline;
this.startLine = payload.startLine;
this.startColumn = payload.startColumn;
/** @type {!Set.<!WebInspector.CSSStyleModel.LiveLocation>} */
this._locations = new Set();
/** @type {!Array.<!WebInspector.SourceMapping>} */
this._sourceMappings = [];
}
WebInspector.CSSStyleSheetHeader.prototype = {
/**
* @return {string}
*/
resourceURL: function()
{
return this.isViaInspector() ? this._viaInspectorResourceURL() : this.sourceURL;
},
/**
* @param {!WebInspector.CSSStyleModel.LiveLocation} location
*/
addLiveLocation: function(location)
{
this._locations.add(location);
location.update();
},
updateLocations: function()
{
var items = this._locations.values();
for (var i = 0; i < items.length; ++i)
items[i].update();
},
/**
* @param {!WebInspector.CSSStyleModel.LiveLocation} location
*/
_removeLocation: function(location)
{
this._locations.remove(location);
},
/**
* @param {number} lineNumber
* @param {number=} columnNumber
* @return {?WebInspector.UILocation}
* @return {!WebInspector.Target}
*/
rawLocationToUILocation: function(lineNumber, columnNumber)
target: function()
{
var uiLocation = null;
var rawLocation = new WebInspector.CSSLocation(this._cssModel.target(), this.id, this.resourceURL(), lineNumber, columnNumber);
for (var i = this._sourceMappings.length - 1; !uiLocation && i >= 0; --i)
uiLocation = this._sourceMappings[i].rawLocationToUILocation(rawLocation);
return uiLocation;
return this._cssModel.target();
},
/**
* @param {!WebInspector.SourceMapping} sourceMapping
* @return {string}
*/
pushSourceMapping: function(sourceMapping)
resourceURL: function()
{
this._sourceMappings.push(sourceMapping);
this.updateLocations();
return this.isViaInspector() ? this._viaInspectorResourceURL() : this.sourceURL;
},
/**
......@@ -1746,8 +1552,7 @@ WebInspector.CSSStyleSheetHeader.prototype = {
isViaInspector: function()
{
return this.origin === "inspector";
},
}
}
/**
......
/*
* Copyright (C) 2013 Google Inc. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following disclaimer
* in the documentation and/or other materials provided with the
* distribution.
* * Neither the name of Google Inc. nor the names of its
* contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
/**
* @constructor
* @param {!WebInspector.CSSStyleModel} cssModel
* @param {!WebInspector.Workspace} workspace
* @param {!WebInspector.NetworkWorkspaceBinding} networkWorkspaceBinding
*/
WebInspector.CSSStyleSheetMapping = function(cssModel, workspace, networkWorkspaceBinding)
{
this._cssModel = cssModel;
this._workspace = workspace;
this._stylesSourceMapping = new WebInspector.StylesSourceMapping(cssModel, workspace);
this._sassSourceMapping = new WebInspector.SASSSourceMapping(cssModel, workspace, networkWorkspaceBinding);
cssModel.addEventListener(WebInspector.CSSStyleModel.Events.StyleSheetAdded, this._styleSheetAdded, this);
cssModel.addEventListener(WebInspector.CSSStyleModel.Events.StyleSheetRemoved, this._styleSheetRemoved, this);
}
WebInspector.CSSStyleSheetMapping.prototype = {
/**
* @param {!WebInspector.Event} event
*/
_styleSheetAdded: function(event)
{
var header = /** @type {!WebInspector.CSSStyleSheetHeader} */ (event.data);
this._stylesSourceMapping.addHeader(header);
this._sassSourceMapping.addHeader(header);
},
/**
* @param {!WebInspector.Event} event
*/
_styleSheetRemoved: function(event)
{
var header = /** @type {!WebInspector.CSSStyleSheetHeader} */ (event.data);
this._stylesSourceMapping.removeHeader(header);
this._sassSourceMapping.removeHeader(header);
}
}
......@@ -4,20 +4,116 @@
/**
* @constructor
* @implements {WebInspector.TargetManager.Observer}
*/
WebInspector.CSSWorkspaceBinding = function()
{
/** @type {!Map.<!WebInspector.Target, !WebInspector.CSSWorkspaceBinding.TargetInfo>} */
this._targetToTargetInfo = new Map();
WebInspector.targetManager.observeTargets(this);
WebInspector.targetManager.addModelListener(WebInspector.ResourceTreeModel, WebInspector.ResourceTreeModel.EventTypes.MainFrameNavigated, this._mainFrameCreatedOrNavigated, this);
}
WebInspector.CSSWorkspaceBinding.prototype = {
/**
* @param {!WebInspector.Target} target
*/
targetAdded: function(target)
{
this._targetToTargetInfo.put(target, new WebInspector.CSSWorkspaceBinding.TargetInfo(target, WebInspector.workspace, WebInspector.networkWorkspaceBinding));
},
/**
* @param {!WebInspector.Target} target
*/
targetRemoved: function(target)
{
this._targetToTargetInfo.remove(target)._dispose();
},
/**
* @param {!WebInspector.CSSStyleSheetHeader} header
* @param {!WebInspector.SourceMapping} mapping
*/
pushSourceMapping: function(header, mapping)
{
this._ensureInfoForHeader(header)._pushSourceMapping(mapping);
},
/**
* @param {!WebInspector.CSSStyleSheetHeader} header
* @return {?WebInspector.CSSWorkspaceBinding.HeaderInfo}
*/
_headerInfo: function(header)
{
var map = this._targetToTargetInfo.get(header.target());
return map._headerInfo(header.id) || null;
},
/**
* @param {!WebInspector.CSSStyleSheetHeader} header
* @return {!WebInspector.CSSWorkspaceBinding.HeaderInfo}
*/
_ensureInfoForHeader: function(header)
{
var targetInfo = this._targetToTargetInfo.get(header.target());
if (!targetInfo) {
targetInfo = new WebInspector.CSSWorkspaceBinding.TargetInfo(header.target(), WebInspector.workspace, WebInspector.networkWorkspaceBinding);
this._targetToTargetInfo.put(header.target(), targetInfo);
}
return targetInfo._ensureInfoForHeader(header);
},
/**
* @param {!WebInspector.Event} event
*/
_mainFrameCreatedOrNavigated: function(event)
{
var target = /** @type {!WebInspector.ResourceTreeModel} */ (event.target).target();
var info = this._targetToTargetInfo.remove(target);
if (info)
info._dispose();
this._targetToTargetInfo.put(target, new WebInspector.CSSWorkspaceBinding.TargetInfo(target, WebInspector.workspace, WebInspector.networkWorkspaceBinding));
},
/**
* @param {!WebInspector.CSSStyleSheetHeader} header
*/
updateLocations: function(header)
{
var info = this._headerInfo(header);
if (info)
info._updateLocations();
},
/**
* @param {!WebInspector.CSSLocation} rawLocation
* @param {function(!WebInspector.UILocation):(boolean|undefined)} updateDelegate
* @return {!WebInspector.CSSStyleModel.LiveLocation}
* @return {!WebInspector.CSSWorkspaceBinding.LiveLocation}
*/
createLiveLocation: function(rawLocation, updateDelegate)
{
return /** @type {!WebInspector.CSSStyleModel.LiveLocation} */ (rawLocation.createLiveLocation(updateDelegate));
var header = rawLocation.styleSheetId ? rawLocation.target().cssModel.styleSheetHeaderForId(rawLocation.styleSheetId) : null;
return new WebInspector.CSSWorkspaceBinding.LiveLocation(rawLocation.target().cssModel, header, rawLocation, updateDelegate);
},
/**
* @param {!WebInspector.CSSWorkspaceBinding.LiveLocation} location
*/
_addLiveLocation: function(location)
{
this._ensureInfoForHeader(location._header)._addLocation(location);
},
/**
* @param {!WebInspector.CSSWorkspaceBinding.LiveLocation} location
*/
_removeLiveLocation: function(location)
{
var info = this._headerInfo(location._header);
if (info)
info._removeLocation(location);
},
/**
......@@ -52,10 +148,250 @@ WebInspector.CSSWorkspaceBinding.prototype = {
*/
rawLocationToUILocation: function(rawLocation)
{
return rawLocation ? rawLocation.target().cssModel.rawLocationToUILocation(rawLocation) : null;
if (!rawLocation)
return null;
var cssModel = rawLocation.target().cssModel;
var frameIdToSheetIds = cssModel.styleSheetIdsByFrameIdForURL(rawLocation.url);
if (!Object.values(frameIdToSheetIds).length)
return null;
var styleSheetIds = [];
for (var frameId in frameIdToSheetIds)
styleSheetIds = styleSheetIds.concat(frameIdToSheetIds[frameId]);
var uiLocation;
for (var i = 0; !uiLocation && i < styleSheetIds.length; ++i) {
var header = cssModel.styleSheetHeaderForId(styleSheetIds[i]);
if (!header)
continue;
var info = this._headerInfo(header);
if (info)
uiLocation = info._rawLocationToUILocation(rawLocation.lineNumber, rawLocation.columnNumber);
}
return uiLocation || null;
}
}
/**
* @constructor
* @param {!WebInspector.Target} target
* @param {!WebInspector.Workspace} workspace
* @param {!WebInspector.NetworkWorkspaceBinding} networkWorkspaceBinding
*/
WebInspector.CSSWorkspaceBinding.TargetInfo = function(target, workspace, networkWorkspaceBinding)
{
this._target = target;
this._workspace = workspace;
var cssModel = target.cssModel;
this._stylesSourceMapping = new WebInspector.StylesSourceMapping(cssModel, workspace);
this._sassSourceMapping = new WebInspector.SASSSourceMapping(cssModel, workspace, networkWorkspaceBinding);
/** @type {!StringMap.<!WebInspector.CSSWorkspaceBinding.HeaderInfo>} */
this._headerInfoById = new StringMap();
cssModel.addEventListener(WebInspector.CSSStyleModel.Events.StyleSheetAdded, this._styleSheetAdded, this);
cssModel.addEventListener(WebInspector.CSSStyleModel.Events.StyleSheetRemoved, this._styleSheetRemoved, this);
}
WebInspector.CSSWorkspaceBinding.TargetInfo.prototype = {
/**
* @param {!WebInspector.Event} event
*/
_styleSheetAdded: function(event)
{
var header = /** @type {!WebInspector.CSSStyleSheetHeader} */ (event.data);
this._stylesSourceMapping.addHeader(header);
this._sassSourceMapping.addHeader(header);
},
/**
* @param {!WebInspector.Event} event
*/
_styleSheetRemoved: function(event)
{
var header = /** @type {!WebInspector.CSSStyleSheetHeader} */ (event.data);
this._stylesSourceMapping.removeHeader(header);
this._sassSourceMapping.removeHeader(header);
this._headerInfoById.remove(header.id);
},
/**
* @param {!CSSAgent.StyleSheetId} id
*/
_headerInfo: function(id)
{
return this._headerInfoById.get(id);
},
_ensureInfoForHeader: function(header)
{
var info = this._headerInfoById.get(header.id);
if (!info) {
info = new WebInspector.CSSWorkspaceBinding.HeaderInfo(header);
this._headerInfoById.put(header.id, info);
}
return info;
},
_dispose: function()
{
this._target.cssModel.removeEventListener(WebInspector.CSSStyleModel.Events.StyleSheetAdded, this._styleSheetAdded, this);
this._target.cssModel.removeEventListener(WebInspector.CSSStyleModel.Events.StyleSheetRemoved, this._styleSheetRemoved, this);
}
}
/**
* @constructor
* @param {!WebInspector.CSSStyleSheetHeader} header
*/
WebInspector.CSSWorkspaceBinding.HeaderInfo = function(header)
{
this._header = header;
/** @type {!Array.<!WebInspector.SourceMapping>} */
this._sourceMappings = [];
/** @type {!Set.<!WebInspector.LiveLocation>} */
this._locations = new Set();
}
WebInspector.CSSWorkspaceBinding.HeaderInfo.prototype = {
/**
* @param {!WebInspector.LiveLocation} location
*/
_addLocation: function(location)
{
this._locations.add(location);
location.update();
},
/**
* @param {!WebInspector.LiveLocation} location
*/
_removeLocation: function(location)
{
this._locations.remove(location);
},
_updateLocations: function()
{
var items = this._locations.values();
for (var i = 0; i < items.length; ++i)
items[i].update();
},
/**
* @param {number} lineNumber
* @param {number=} columnNumber
* @return {?WebInspector.UILocation}
*/
_rawLocationToUILocation: function(lineNumber, columnNumber)
{
var uiLocation = null;
var rawLocation = new WebInspector.CSSLocation(this._header.target(), this._header.id, this._header.resourceURL(), lineNumber, columnNumber);
for (var i = this._sourceMappings.length - 1; !uiLocation && i >= 0; --i)
uiLocation = this._sourceMappings[i].rawLocationToUILocation(rawLocation);
return uiLocation;
},
/**
* @param {!WebInspector.SourceMapping} sourceMapping
*/
_pushSourceMapping: function(sourceMapping)
{
this._sourceMappings.push(sourceMapping);
this._updateLocations();
}
}
/**
* @constructor
* @extends {WebInspector.LiveLocation}
* @param {!WebInspector.CSSStyleModel} cssModel
* @param {?WebInspector.CSSStyleSheetHeader} header
* @param {!WebInspector.CSSLocation} rawLocation
* @param {function(!WebInspector.UILocation):(boolean|undefined)} updateDelegate
*/
WebInspector.CSSWorkspaceBinding.LiveLocation = function(cssModel, header, rawLocation, updateDelegate)
{
WebInspector.LiveLocation.call(this, rawLocation, updateDelegate);
this._cssModel = cssModel;
if (!header)
this._clearStyleSheet();
else
this._setStyleSheet(header);
}
WebInspector.CSSWorkspaceBinding.LiveLocation.prototype = {
/**
* @param {!WebInspector.Event} event
*/
_styleSheetAdded: function(event)
{
console.assert(!this._header);
var header = /** @type {!WebInspector.CSSStyleSheetHeader} */ (event.data);
if (header.sourceURL && header.sourceURL === this.rawLocation().url)
this._setStyleSheet(header);
},
/**
* @param {!WebInspector.Event} event
*/
_styleSheetRemoved: function(event)
{
console.assert(this._header);
var header = /** @type {!WebInspector.CSSStyleSheetHeader} */ (event.data);
if (this._header !== header)
return;
WebInspector.cssWorkspaceBinding._removeLiveLocation(this);
this._clearStyleSheet();
},
/**
* @param {!WebInspector.CSSStyleSheetHeader} header
*/
_setStyleSheet: function(header)
{
this._header = header;
WebInspector.cssWorkspaceBinding._addLiveLocation(this);
this._cssModel.removeEventListener(WebInspector.CSSStyleModel.Events.StyleSheetAdded, this._styleSheetAdded, this);
this._cssModel.addEventListener(WebInspector.CSSStyleModel.Events.StyleSheetRemoved, this._styleSheetRemoved, this);
},
_clearStyleSheet: function()
{
delete this._header;
this._cssModel.removeEventListener(WebInspector.CSSStyleModel.Events.StyleSheetRemoved, this._styleSheetRemoved, this);
this._cssModel.addEventListener(WebInspector.CSSStyleModel.Events.StyleSheetAdded, this._styleSheetAdded, this);
},
/**
* @return {?WebInspector.UILocation}
*/
uiLocation: function()
{
var cssLocation = /** @type WebInspector.CSSLocation */ (this.rawLocation());
if (this._header) {
var headerInfo = WebInspector.cssWorkspaceBinding._headerInfo(this._header);
return headerInfo._rawLocationToUILocation(cssLocation.lineNumber, cssLocation.columnNumber);
}
var uiSourceCode = WebInspector.workspace.uiSourceCodeForURL(cssLocation.url);
if (!uiSourceCode)
return null;
return uiSourceCode.uiLocation(cssLocation.lineNumber, cssLocation.columnNumber);
},
dispose: function()
{
WebInspector.LiveLocation.prototype.dispose.call(this);
if (this._header)
WebInspector.cssWorkspaceBinding._removeLiveLocation(this);
this._cssModel.removeEventListener(WebInspector.CSSStyleModel.Events.StyleSheetAdded, this._styleSheetAdded, this);
this._cssModel.removeEventListener(WebInspector.CSSStyleModel.Events.StyleSheetRemoved, this._styleSheetRemoved, this);
},
__proto__: WebInspector.LiveLocation.prototype
}
/**
* @type {!WebInspector.CSSWorkspaceBinding}
*/
......
......@@ -419,7 +419,7 @@ WebInspector.SASSSourceMapping.prototype = {
var completeSourceMapURL = WebInspector.ParsedURL.completeURL(sourceURL, header.sourceMapURL);
if (completeSourceMapURL)
delete this._sourceMapByURL[completeSourceMapURL];
header.updateLocations();
WebInspector.cssWorkspaceBinding.updateLocations(header);
},
/**
......@@ -445,7 +445,7 @@ WebInspector.SASSSourceMapping.prototype = {
this._sourceMapByStyleSheetURL[sourceURL] = sourceMap;
for (var i = 0; i < headersWithSameSourceURL.length; ++i) {
if (forceRebind)
headersWithSameSourceURL[i].updateLocations();
WebInspector.cssWorkspaceBinding.updateLocations(headersWithSameSourceURL[i]);
else
this._bindUISourceCode(headersWithSameSourceURL[i], sourceMap);
}
......@@ -519,7 +519,7 @@ WebInspector.SASSSourceMapping.prototype = {
*/
_bindUISourceCode: function(header, sourceMap)
{
header.pushSourceMapping(this);
WebInspector.cssWorkspaceBinding.pushSourceMapping(header, this);
var rawURL = header.sourceURL;
var sources = sourceMap.sources();
for (var i = 0; i < sources.length; ++i) {
......@@ -604,7 +604,7 @@ WebInspector.SASSSourceMapping.prototype = {
for (var j = 0; j < ids.length; ++j) {
var header = this._cssModel.styleSheetHeaderForId(ids[j]);
console.assert(header);
header.updateLocations();
WebInspector.cssWorkspaceBinding.updateLocations(/** @type {!WebInspector.CSSStyleSheetHeader} */ (header));
}
}
},
......
......@@ -110,7 +110,7 @@ WebInspector.StylesSourceMapping.prototype = {
if (!url)
return;
header.pushSourceMapping(this);
WebInspector.cssWorkspaceBinding.pushSourceMapping(header, this);
var map = this._urlToHeadersByFrameId[url];
if (!map) {
map = /** @type {!StringMap.<!StringMap.<!WebInspector.CSSStyleSheetHeader>>} */ (new StringMap());
......@@ -187,7 +187,7 @@ WebInspector.StylesSourceMapping.prototype = {
return;
var url = uiSourceCode.url;
this._styleFiles.put(uiSourceCode, new WebInspector.StyleFile(uiSourceCode, this));
header.updateLocations();
WebInspector.cssWorkspaceBinding.updateLocations(header);
},
/**
......
......@@ -38,7 +38,6 @@
"sdk/CSSMetadata.js",
"sdk/CSSParser.js",
"sdk/CSSStyleModel.js",
"sdk/CSSStyleSheetMapping.js",
"sdk/CSSWorkspaceBinding.js",
"sdk/BreakpointManager.js",
"sdk/DOMModel.js",
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment