diff --git a/src/plugins/debugger/debuggerengine.h b/src/plugins/debugger/debuggerengine.h
index e18e763e16912521fcf29324b31864867bea4662..b400435e8a970bb42fa03b345e50ff290c46e824 100644
--- a/src/plugins/debugger/debuggerengine.h
+++ b/src/plugins/debugger/debuggerengine.h
@@ -80,7 +80,10 @@ public:
     // for qml debugging
     QString qmlServerAddress;
     quint16 qmlServerPort;
-    DebuggerEngineType cppEngineType; // for cpp+qml debugging
+    QString projectBuildDir;
+    QString projectDir;
+    // for cpp+qml debugging
+    DebuggerEngineType cppEngineType;
 
     // for remote debugging
     QString remoteChannel;
@@ -274,8 +277,8 @@ public:
 
     void resetLocation();
     void openFile(const QString &fileName, int lineNumber = -1);
-    void gotoLocation(const QString &fileName, int lineNumber, bool setMarker);
-    void gotoLocation(const StackFrame &frame, bool setMarker);
+    virtual void gotoLocation(const QString &fileName, int lineNumber, bool setMarker);
+    virtual void gotoLocation(const StackFrame &frame, bool setMarker);
     virtual void quitDebugger(); // called by DebuggerRunControl
 
 signals:
diff --git a/src/plugins/debugger/debuggerrunner.cpp b/src/plugins/debugger/debuggerrunner.cpp
index e8d3dfc909d199ded7af72767d8a034fc33227b8..310e8ce36fcf4a1f437cc97ccc82515a2becb873 100644
--- a/src/plugins/debugger/debuggerrunner.cpp
+++ b/src/plugins/debugger/debuggerrunner.cpp
@@ -156,6 +156,10 @@ static DebuggerStartParameters localStartParameters(RunConfiguration *runConfigu
         sp.qmlServerAddress = QLatin1String("127.0.0.1");
         sp.qmlServerPort = runConfiguration->qmlDebugServerPort();
 
+        sp.projectDir = runConfiguration->target()->project()->projectDirectory();
+        if (runConfiguration->target()->activeBuildConfiguration())
+            sp.projectBuildDir = runConfiguration->target()->activeBuildConfiguration()->buildDirectory();
+
         sp.environment << QString(Constants::E_QML_DEBUG_SERVER_PORT)
                         + QLatin1Char('=') + QString::number(sp.qmlServerPort);
     }
diff --git a/src/plugins/debugger/qml/qmlengine.cpp b/src/plugins/debugger/qml/qmlengine.cpp
index 2cd0f9b639588ef7383d958f0e3821a2a0839693..d8c2ac69c4601073808b53d219774da96366d570 100644
--- a/src/plugins/debugger/qml/qmlengine.cpp
+++ b/src/plugins/debugger/qml/qmlengine.cpp
@@ -126,6 +126,25 @@ void QmlEngine::pauseConnection()
     m_adapter->pauseConnection();
 }
 
+void QmlEngine::gotoLocation(const QString &fileName, int lineNumber, bool setMarker)
+{
+    QString processedFilename = fileName;
+
+    if (isShadowBuildProject())
+        processedFilename = fromShadowBuildFilename(fileName);
+
+    DebuggerEngine::gotoLocation(processedFilename, lineNumber, setMarker);
+}
+
+void QmlEngine::gotoLocation(const StackFrame &frame, bool setMarker)
+{
+    StackFrame adjustedFrame = frame;
+    if (isShadowBuildProject())
+        adjustedFrame.file = fromShadowBuildFilename(frame.file);
+
+    DebuggerEngine::gotoLocation(adjustedFrame, setMarker);
+}
+
 void QmlEngine::setupInferior()
 {
     QTC_ASSERT(state() == InferiorSetupRequested, qDebug() << state());
@@ -380,7 +399,10 @@ void QmlEngine::attemptBreakpointSynchronization()
     QSet< QPair<QString, qint32> > breakList;
     for (int index = 0; index != handler->size(); ++index) {
         BreakpointData *data = handler->at(index);
-        breakList << qMakePair(data->fileName, data->lineNumber.toInt());
+        QString processedFilename = data->fileName;
+        if (isShadowBuildProject())
+            processedFilename = toShadowBuildFilename(data->fileName);
+        breakList << qMakePair(processedFilename, data->lineNumber.toInt());
     }
 
     {
@@ -677,6 +699,73 @@ void QmlEngine::executeDebuggerCommand(const QString& command)
     sendMessage(reply);
 }
 
+bool QmlEngine::isShadowBuildProject() const
+{
+    if (!startParameters().projectBuildDir.isEmpty()
+        && (startParameters().projectDir != startParameters().projectBuildDir))
+    {
+        return true;
+    }
+    return false;
+}
+
+QString QmlEngine::qmlImportPath() const
+{
+    QString result;
+    const QString qmlImportPathPrefix("QML_IMPORT_PATH=");
+    QStringList env = startParameters().environment;
+    foreach(const QString &envStr, env) {
+        if (envStr.startsWith(qmlImportPathPrefix)) {
+            result = envStr.mid(qmlImportPathPrefix.length());
+            break;
+        }
+    }
+    return result;
+}
+
+QString QmlEngine::toShadowBuildFilename(const QString &filename) const
+{
+    QString newFilename = filename;
+    QString importPath = qmlImportPath();
+
+    newFilename = mangleFilenamePaths(filename, startParameters().projectDir, startParameters().projectBuildDir);
+    if (newFilename == filename && !importPath.isEmpty()) {
+        newFilename = mangleFilenamePaths(filename, startParameters().projectDir, importPath);
+    }
+
+    return newFilename;
+}
+
+QString QmlEngine::mangleFilenamePaths(const QString &filename, const QString &oldBasePath, const QString &newBasePath) const
+{
+    QDir oldBaseDir(oldBasePath);
+    QDir newBaseDir(newBasePath);
+    QFileInfo fileInfo(filename);
+
+    if (oldBaseDir.exists() && newBaseDir.exists() && fileInfo.exists()) {
+        if (fileInfo.absoluteFilePath().startsWith(oldBaseDir.canonicalPath())) {
+            QString fileRelativePath = fileInfo.canonicalFilePath().mid(oldBasePath.length());
+            QFileInfo projectFile(newBaseDir.canonicalPath() + QLatin1Char('/') + fileRelativePath);
+
+            if (projectFile.exists())
+                return projectFile.canonicalFilePath();
+        }
+    }
+    return filename;
+}
+
+QString QmlEngine::fromShadowBuildFilename(const QString &filename) const
+{
+    QString newFilename = filename;
+    QString importPath = qmlImportPath();
+
+    newFilename = mangleFilenamePaths(filename, startParameters().projectBuildDir, startParameters().projectDir);
+    if (newFilename == filename && !importPath.isEmpty()) {
+        newFilename = mangleFilenamePaths(filename, startParameters().projectBuildDir, importPath);
+    }
+
+    return newFilename;
+}
 
 } // namespace Internal
 } // namespace Debugger
diff --git a/src/plugins/debugger/qml/qmlengine.h b/src/plugins/debugger/qml/qmlengine.h
index 9c02c2c4cb7e16f9ce24b84b995a7c27ddaffc88..5c0854acf28045f7a4f777215365a76e00eceebd 100644
--- a/src/plugins/debugger/qml/qmlengine.h
+++ b/src/plugins/debugger/qml/qmlengine.h
@@ -67,6 +67,8 @@ public:
     void shutdownInferiorAsSlave();
     void shutdownEngineAsSlave();
     void pauseConnection();
+    void gotoLocation(const QString &fileName, int lineNumber, bool setMarker);
+    void gotoLocation(const StackFrame &frame, bool setMarker);
 
 public slots:
     void messageReceived(const QByteArray &message);
@@ -130,6 +132,12 @@ private:
     void expandObject(const QByteArray &iname, quint64 objectId);
     void sendPing();
 
+    bool isShadowBuildProject() const;
+    QString fromShadowBuildFilename(const QString &filename) const;
+    QString mangleFilenamePaths(const QString &filename, const QString &oldBasePath, const QString &newBasePath) const;
+    QString toShadowBuildFilename(const QString &filename) const;
+    QString qmlImportPath() const;
+
 private:
     friend class QmlCppEngine;