/* Device-specific code */

// Device resolutions. Can be used for device-specific customization.
var RESOLUTION_UNDEFINED = 0;
var RESOLUTION_QVGA_LANDSCAPE = 1;  // 320x240
var RESOLUTION_QVGA_PORTRAIT = 2;   // 240x320
var RESOLUTION_NHD_LANDSCAPE = 3;   // 640x360
var RESOLUTION_NHD_PORTRAIT = 4;    // 360x640
var RESOLUTION_E90_LANDSCAPE = 5;   // 800x352
var resolution = RESOLUTION_UNDEFINED;

var touchSupported = false;

// TODO: Remove this when there's no more need for automatic resolution
// polling
var timer = null;

// Does the device-specific customizations
function devSpecificInit() {
    // Call switchOrientation to get the orientation detected correctly
    switchOrientation();
    if (resolution == RESOLUTION_NHD_LANDSCAPE ||
        resolution == RESOLUTION_NHD_PORTRAIT) {
        customizeForNHD();
    }

    customizeForTUI();
    
    customizeNavigationBar();

    // TODO: Remove this when there's no more need for automatic resolution
    // polling.
    // Observe changes in orientation at one second intervals
    timer = setInterval("tick()", 1000);
}

// Customizes the styles for nHD displays (regardless of the orientation)
function customizeForNHD() {
    var h2Elements = document.getElementsByTagName("h2");
    for (var i = 0; i < h2Elements.length; i++) {
        h2Elements[i].style.fontSize = "1.7em";
    }

    var textualForecastElement = document.getElementById("textualForecast");
    textualForecastElement.style.marginTop = "2.5em";
    textualForecastElement.style.fontSize = "1.5em";
}

// Does touch-specific customizations
function customizeForTUI() {
    detectTouchUI();
    if (touchSupported) {
        // Remove the highlight
        locationNodes[currentlySelectedLocation].removeAttribute("class");
    } else {
        // Create the menu
        createMenu();
    }
}

// Centers the navigation bar vertically
// TODO: This whole function is a hack for working around the navigation bar
// centering issue (see the Known issues section of the release notes for more
// information)
function customizeNavigationBar() {
    var topValue = "1em";  // for undefined resolutions
    if (resolution == RESOLUTION_QVGA_PORTRAIT ||
        resolution == RESOLUTION_NHD_LANDSCAPE) {
        topValue = "5em";
    } else if (resolution == RESOLUTION_QVGA_LANDSCAPE) {
        topValue = "4em";
    } else if (resolution == RESOLUTION_NHD_PORTRAIT) {
        topValue = "10em";
    } else if (resolution == RESOLUTION_E90_LANDSCAPE) {
        topValue = "3em";
    }
    
    document.getElementById("navigationLeft").style.top = topValue;
    document.getElementById("navigationRight").style.top = topValue;
}

// TODO: This is a hack that acts as a workaround for shortcomings of the
// JavaScript support on the device; namely, the lack of the document.onresize
// event.
// <hack>

// Called when the timer's interval elapses
function tick() {
    windowResized();
}
// </hack>

// Gets called when the window is resized.
// TODO: Unfortunately, this function is never called on the device, because
// (currently) it doesn't support the document.onresize event.
function windowResized() {
    switchOrientation();
}

// Does the device-specific style customizations according to the orientation
// of the screen
function switchOrientation() {
    // TODO: Remove this when there's no more need for automatic resolution
    // polling
    var prevResolution = resolution;    

    // Detect the new resolution.
    detectResolution();

    // If the resolution hasn't changed, there's no need to do anything.
    // TODO: This is a hack that relates to automatic resolution polling. If
    // this function (switchOrientation) were called only after the resolution
    // really had changed (from the windowResized function), there would be no
    // need for this check.
    if (resolution == prevResolution) {
        return;
    }
    
    resetStyles();
    
    if (resolution == RESOLUTION_QVGA_LANDSCAPE) {
        var h2Elements = document.getElementsByTagName("h2");
        for (var i = 0; i < h2Elements.length; i++) {
            h2Elements[i].style.margin = "3% 0 0 0";
        }

        var locationTableElement = document.getElementById("locationTable");
        var locationTdElements = locationTableElement.getElementsByTagName("td");
        for (var i = 0; i < locationTdElements.length; i++) {
            locationTdElements[i].style.width = "48px";
            locationTdElements[i].style.height = "48px";
            locationTdElements[i].style.fontSize = "68%";
        }
    } else if (resolution == RESOLUTION_QVGA_PORTRAIT) {
        var h2Elements = document.getElementsByTagName("h2");
        for (var i = 0; i < h2Elements.length; i++) {
            h2Elements[i].style.margin = "7% 0 5% 0";
        }
        
        var locationTableElement = document.getElementById("locationTable");
        var locationTdElements = locationTableElement.getElementsByTagName("td");
        for (var i = 0; i < locationTdElements.length; i++) {
            locationTdElements[i].style.width = "54px";
            locationTdElements[i].style.height = "54px";
            locationTdElements[i].style.fontSize = "80%";
        }
    } else if (resolution == RESOLUTION_NHD_LANDSCAPE) {
        var locationTableElement = document.getElementById("locationTable");
        locationTableElement.style.marginTop = "0";

        var locationTdElements = locationTableElement.getElementsByTagName("td");
        for (var i = 0; i < locationTdElements.length; i++) {
            locationTdElements[i].style.width = "90px";
            locationTdElements[i].style.height = "90px";
            locationTdElements[i].style.fontSize = "1em";
        }

        var temperaturesElement = document.getElementById("temperatures");
        temperaturesElement.setAttribute("class", "rightAligned");

        var forecastElement = document.getElementById("forecast");
        forecastElement.style.marginBottom = "0";

        var gForecastElement = document.getElementById("graphicalForecast");
        forecastElement.insertBefore(temperaturesElement, gForecastElement);
    } else if (resolution == RESOLUTION_NHD_PORTRAIT) {
        var locationTableElement = document.getElementById("locationTable");
        locationTableElement.style.marginTop = "30%";

        var locationTdElements = locationTableElement.getElementsByTagName("td");
        for (var i = 0; i < locationTdElements.length; i++) {
            locationTdElements[i].style.width = "90px";
            locationTdElements[i].style.height = "90px";
            locationTdElements[i].style.fontSize = "1em";
        }
    } else if (resolution == RESOLUTION_E90_LANDSCAPE) {
        var h2Elements = document.getElementsByTagName("h2");
        for (var i = 0; i < h2Elements.length; i++) {
            h2Elements[i].style.margin = "3% 0";
        }

        var locationTableElement = document.getElementById("locationTable");
        locationTableElement.style.borderSpacing = "3em 0";

        var locationTdElements = locationTableElement.getElementsByTagName("td");
        for (var i = 0; i < locationTdElements.length; i++) {
            locationTdElements[i].style.width = "62px";
            locationTdElements[i].style.height = "62px";
            locationTdElements[i].style.fontSize = "0.9em";
        }

        var temperaturesElement = document.getElementById("temperatures");
        temperaturesElement.setAttribute("class", "rightAligned");

        var forecastElement = document.getElementById("forecast");
        forecastElement.style.marginBottom = "0";

        var gForecastElement = document.getElementById("graphicalForecast");
        forecastElement.insertBefore(temperaturesElement, gForecastElement);

        var tForecastElement = document.getElementById("textualForecast");
        tForecastElement.style.marginTop = "6%";

        var lNavigation = document.getElementById("navigationLeft");
        lNavigation.style.marginLeft = "50px";

        var rNavigation = document.getElementById("navigationRight");
        rNavigation.style.marginRight = "50px";
    }
    
    // TODO: This won't be needed anymore when the navigation bar centering
    // issue will get fixed
    customizeNavigationBar();
}

// Resets styles according to the unmodified CSS. Naturally, this concerns only
// the styles that are modified in this file (dev_specific.js).
function resetStyles() {
    var locationTableElement = document.getElementById("locationTable");
    locationTableElement.style.borderSpacing = "1em 0";

    var temperaturesElement = document.getElementById("temperatures");
    temperaturesElement.setAttribute("class", "footer");

    var forecastElement = document.getElementById("forecast");
    forecastElement.style.marginBottom = "-49px";

    var forecastContainerElement = document.getElementById("forecastContainer");
    forecastContainerElement.appendChild(temperaturesElement);

    var tForecastElement = document.getElementById("textualForecast");
    tForecastElement.style.marginTop = "0";

    var lNavigation = document.getElementById("navigationLeft");
    lNavigation.style.marginLeft = "0";

    var rNavigation = document.getElementById("navigationRight");
    rNavigation.style.marginRight = "0";
}

// Identifies the device by querying its resolution
function detectResolution() {
    var screenWidth = screen.width;
    var screenHeight = screen.height;
    
    if (screenWidth == 240 && screenHeight == 320) {
        resolution = RESOLUTION_QVGA_PORTRAIT;
    } else if (screenWidth == 320 && screenHeight == 240) {
        resolution = RESOLUTION_QVGA_LANDSCAPE;
    } else if (screenWidth == 360 && screenHeight == 640) {
        resolution = RESOLUTION_NHD_PORTRAIT;
    } else if (screenWidth == 640 && screenHeight == 360) {
        resolution = RESOLUTION_NHD_LANDSCAPE;
    } else if (screenWidth == 800 && screenHeight == 352) {
        resolution = RESOLUTION_E90_LANDSCAPE;
    } else {
        resolution = RESOLUTION_UNDEFINED;
    }
}

// Detects whether touch UI is supported
function detectTouchUI() {
    // <hack>
    // There's no better way to detect whether touch UI is supported than
    // querying the device resolution. This is terrible, because nothing
    // guarantees that there won't be non-touch-enabled devices with this
    // resolution in the future.
    if (resolution == RESOLUTION_NHD_LANDSCAPE ||
        resolution == RESOLUTION_NHD_PORTRAIT) {
        touchSupported = true;
    } else {
        touchSupported = false;
    }
    // </hack>
}

// Called when a location is selected
function locationSelected(elementNumber, locationCode, locationText) {
    if (!touchSupported) {
        fetch(elementNumber, locationCode, locationText);
    } else {
        doClickEffect(elementNumber, locationCode, locationText);
    }
}

// Gives visual feedback about clicking on a city icon
function doClickEffect(elementNumber, locationCode, locationText) {
    if (locationNodes[elementNumber].getAttribute("class") != "clickedItem") {
        locationNodes[elementNumber].setAttribute("class", "clickedItem");

        // Show the "clicked" picture
        var imageElement = locationNodes[elementNumber].getElementsByTagName("img")[0];
        var imageSource = imageElement.getAttribute("src");
        var extensionIndex = imageSource.lastIndexOf(".");
        var imagePath = imageSource.substring(0, extensionIndex);
        var imageExtension = imageSource.substring(extensionIndex);
        imageElement.setAttribute("src", imagePath + "_clicked" + imageExtension);
        
        // Call this function again after half a second
        var parameterList = elementNumber + ", " + (locationCode == null ? null : "'" +
            locationCode + "'") + ", '" + locationText + "'";
        setTimeout("doClickEffect(" + parameterList + ")", 500);
    } else {
        locationNodes[elementNumber].removeAttribute("class");

        // Show the normal picture
        var imageElement = locationNodes[elementNumber].getElementsByTagName("img")[0];
        var imageSource = imageElement.getAttribute("src");
        var underscoreIndex = imageSource.lastIndexOf("_");
        var imagePath = imageSource.substring(0, underscoreIndex);
        var extensionIndex = imageSource.lastIndexOf(".");
        var imageExtension = imageSource.substring(extensionIndex);
        imageElement.setAttribute("src", imagePath + imageExtension);
        
        fetch(elementNumber, locationCode, locationText);
    }
}

