Project

General

Profile

Bug #128 » xbmc4xbox-weather.diff

weather ripped out - nuka1195, 29/12/2010 09:10 PM

View differences:

skin/Confluence/720p/Home.xml (working copy)
<include>VisibleFadeEffect</include>
<visible>Skin.HasSetting(homepageSysteminfo) + Container(9000).HasFocus(5)</visible>
<animation effect="slide" start="0,0" end="-60,0" delay="0" time="300" condition="Window.IsVisible(MuteBug)">conditional</animation>
<animation effect="slide" start="0,0" end="130,0" delay="0" time="300" condition="Skin.HasSetting(homepageWeatherinfo) | !IsTrue(Window(Weather).Property(Weather.IsFetched))">conditional</animation>
<animation effect="slide" start="0,0" end="130,0" delay="0" time="300" condition="Skin.HasSetting(homepageWeatherinfo) | !Weather.IsFetched">conditional</animation>
<animation effect="slide" start="0,0" end="840,0" delay="0" time="300">WindowClose</animation>
<animation effect="slide" start="840,0" end="0,0" delay="0" time="300">WindowOpen</animation>
<control type="image">
......
<animation effect="slide" start="0,0" end="-60,0" delay="0" time="300" condition="Window.IsVisible(MuteBug)">conditional</animation>
<animation effect="slide" start="0,0" end="510,0" delay="0" time="300">WindowClose</animation>
<animation effect="slide" start="510,0" end="0,0" delay="0" time="300">WindowOpen</animation>
<visible>!Skin.HasSetting(homepageWeatherinfo) + IsTrue(Window(Weather).Property(Weather.IsFetched))</visible>
<visible>!Skin.HasSetting(homepageWeatherinfo) + Weather.IsFetched</visible>
<control type="image">
<description>time background</description>
<posx>0</posx>
skin/Confluence/720p/includes.xml (working copy)
<timeperimage>10000</timeperimage>
<randomize>true</randomize>
<fadetime>1000</fadetime>
<visible>![Skin.HasSetting(ShowWeatherFanart) + !IsEmpty(Skin.String(WeatherFanartDir))]</visible>
<visible>![Skin.HasSetting(ShowWeatherFanart) + !IsEmpty(Window(Weather).Property(Current.FanartPath)]</visible>
</control>
<control type="multiimage">
<posx>0</posx>
......
<timeperimage>10000</timeperimage>
<randomize>true</randomize>
<fadetime>1000</fadetime>
<visible>Skin.HasSetting(ShowWeatherFanart) + !IsEmpty(Skin.String(WeatherFanartDir))</visible>
<visible>Skin.HasSetting(ShowWeatherFanart) + !IsEmpty(Window(Weather).Property(Current.FanartPath))</visible>
<animation effect="fade" time="200">WindowClose</animation>
</control>
</include>
skin/Confluence/720p/IncludesHomeHorizontal.xml (working copy)
<icon>special://skin/backgrounds/weather.jpg</icon>
<thumb>$INFO[Skin.String(Home_Custom_Back_Weather_Folder)]</thumb>
<visible>!Skin.HasSetting(HomeMenuNoWeatherButton)</visible>
<visible>!Skin.HasSetting(ShowWeatherFanart) | IsEmpty(Skin.String(WeatherFanartDir))</visible>
<visible>!Skin.HasSetting(ShowWeatherFanart) | IsEmpty(Window(Weather).Property(Current.FanartPath))</visible>
</item>
<item id="6">
<label>8</label>
......
<icon>special://skin/backgrounds/weather.jpg</icon>
<thumb>$INFO[Window(Weather).Property(Current.FanartPath)]</thumb>
<visible>!Skin.HasSetting(HomeMenuNoWeatherButton)</visible>
<visible>Skin.HasSetting(ShowWeatherFanart) + !IsEmpty(Skin.String(WeatherFanartDir))</visible>
<visible>Skin.HasSetting(ShowWeatherFanart) + !IsEmpty(Window(Weather).Property(Current.FanartPath))</visible>
</item>
<item id="4">
<label>1</label>
skin/Confluence/720p/IncludesHomeVertical.xml (working copy)
<icon>special://skin/backgrounds/weather.jpg</icon>
<thumb>$INFO[Skin.String(Home_Custom_Back_Weather_Folder)]</thumb>
<visible>!Skin.HasSetting(HomeMenuNoWeatherButton)</visible>
<visible>!Skin.HasSetting(ShowWeatherFanart) | IsEmpty(Skin.String(WeatherFanartDir))</visible>
<visible>!Skin.HasSetting(ShowWeatherFanart) | IsEmpty(Window(Weather).Property(Current.FanartPath))</visible>
</item>
<item id="6">
<label>8</label>
......
<icon>special://skin/backgrounds/weather.jpg</icon>
<thumb>$INFO[Window(Weather).Property(Current.FanartPath)]</thumb>
<visible>!Skin.HasSetting(HomeMenuNoWeatherButton)</visible>
<visible>Skin.HasSetting(ShowWeatherFanart) + !IsEmpty(Skin.String(WeatherFanartDir))</visible>
<visible>Skin.HasSetting(ShowWeatherFanart) + !IsEmpty(Window(Weather).Property(Current.FanartPath))</visible>
</item>
<item id="4">
<label>1</label>
skin/Confluence/720p/script.weather.com.plus/WeatherPluginView.xml (working copy)
<!-- views -->
<control type="group" id="3000">
<include>TWC.Current</include>
<!--include>TWC.Tomorrow</include-->
<include>TWC.36Hour</include>
<include>TWC.Weekend</include>
<include>TWC.Hourly</include>
<include>TWC.Daily</include>
<include>TWC.Maps</include>
<include>TWC.Alerts</include>
<include>TWC.Video</include>
</control>
<!-- The Extra Labels for the above buttons button -->
<control type="grouplist">
......
<ondown>2000</ondown>
<pagecontrol>-</pagecontrol>
<include>TWC.Current.ButtonXLabel</include>
<!--include>TWC.Tomorrow.ButtonXLabel</include-->
<include>TWC.36Hour.ButtonXLabel</include>
<include>TWC.Weekend.ButtonXLabel</include>
<include>TWC.Hourly.ButtonXLabel</include>
<include>TWC.10Day.ButtonXLabel</include>
<include>TWC.Maps.ButtonXLabel</include>
<include>TWC.Alerts.ButtonXLabel</include>
<include>TWC.Video.ButtonXLabel</include>
</control>
<!-- Main Menu Buttons -->
<control type="grouplist" id="2000">
......
<ondown>2000</ondown>
<pagecontrol>-</pagecontrol>
<include>TWC.Current.Button</include>
<!--include>TWC.Tomorrow.Button</include-->
<include>TWC.36Hour.Button</include>
<include>TWC.Weekend.Button</include>
<include>TWC.Hourly.Button</include>
<include>TWC.10Day.Button</include>
<include>TWC.Maps.Button</include>
<include>TWC.Alerts.Button</include>
<include>TWC.Video.Button</include>
</control>
</control>
</control>
......
<visible>!StringCompare(Window.Property(Weather.CurrentView),Skin.String(TWC.DefaultView))</visible>
</control>
<!-- dummy buttons for defaultmap -->
<include>TWC.Maps.DummyButtons</include>
<control type="grouplist" id="9010"><!-- misc options slide -->
<posx>10</posx>
<posy>250</posy>
......
<enable>!StringCompare(Window.Property(Weather.CurrentView),$LOCALIZE[31907] - $LOCALIZE[31914]) + !StringCompare(Window.Property(Weather.CurrentView),$LOCALIZE[31906] - $LOCALIZE[31913])</enable>
</control>
<include>TWC.Current.SettingsButtons</include>
<include>TWC.36Hour.SettingsButtons</include>
<!--include>TWC.Hourly.SettingsButtons</include-->
<include>TWC.Maps.SettingsButtons</include>
<include>TWC.Weekend.SettingsButtons</include>
<include>TWC.10Day.SettingsButtons</include>
<!--include>TWC.Alerts.SettingsButtons</include-->
<control type="label" id="90220">
<width>220</width>
<height>45</height>
xbmc/GUIWindowWeather.cpp (working copy)
void CGUIWindowWeather::CallPlugin()
{
SetProperty("Weather.IsFetched", false);
SetProperty("Weather.IsFetched", "false");
if (g_guiSettings.GetString("weather.plugin").IsEmpty()) return;
xbmc/utils/Weather.cpp (working copy)
#include "stdafx.h"
#include "Weather.h"
#include "FileSystem/ZipManager.h"
#include "FileSystem/RarManager.h"
#include "FileSystem/FileCurl.h"
#include "XMLUtils.h"
#include "Temperature.h"
#include "xbox/network.h"
#include "../Util.h"
#include "Application.h"
#include "GUISettings.h"
#include "GUIWindowManager.h"
#include "GUIDialogProgress.h"
#include "GUIDialogSelect.h"
#include "DateTime.h"
#include "FileSystem/Directory.h"
#include "GUIMediaWindow.h"
#include "ScriptSettings.h"
#include "GUIDialogPluginSettings.h"
using namespace std;
using namespace DIRECTORY;
#define CONTROL_BTNREFRESH 2
#define CONTROL_SELECTLOCATION 3
#define CONTROL_LABELLOCATION 10
#define CONTROL_LABELUPDATED 11
#define CONTROL_IMAGELOGO 101
#define CONTROL_IMAGENOWICON 21
#define CONTROL_LABELNOWCOND 22
#define CONTROL_LABELNOWTEMP 23
#define CONTROL_LABELNOWFEEL 24
#define CONTROL_LABELNOWUVID 25
#define CONTROL_LABELNOWWIND 26
#define CONTROL_LABELNOWDEWP 27
#define CONTROL_LABELNOWHUMI 28
#define CONTROL_STATICTEMP 223
#define CONTROL_STATICFEEL 224
#define CONTROL_STATICUVID 225
#define CONTROL_STATICWIND 226
#define CONTROL_STATICDEWP 227
#define CONTROL_STATICHUMI 228
#define CONTROL_LABELD0DAY 31
#define CONTROL_LABELD0HI 32
#define CONTROL_LABELD0LOW 33
#define CONTROL_LABELD0GEN 34
#define CONTROL_IMAGED0IMG 35
#define PARTNER_ID "1004124588" //weather.com partner id
#define PARTNER_KEY "079f24145f208494" //weather.com partner key
#define MAX_LOCATION 10
#define LOCALIZED_TOKEN_FIRSTID 370
#define LOCALIZED_TOKEN_LASTID 395
#define LOCALIZED_TOKEN_FIRSTID2 1396
#define LOCALIZED_TOKEN_LASTID2 1450
/*
FIXME'S
>strings are not centered
>weather.com dev account is mine not a general xbmc one
*/
// USE THESE FOR ZIP
//#define WEATHER_USE_ZIP 1
//#define WEATHER_USE_RAR 0
//#define WEATHER_BASE_PATH "special://temp/weather/"
//#define WEATHER_SOURCE_FILE "special://xbmc/media/weather.zip"
// OR THESE FOR RAR
#define WEATHER_BASE_PATH "special://temp/weather/"
#define WEATHER_USE_ZIP 0
#define WEATHER_USE_RAR 1
#define WEATHER_SOURCE_FILE "special://xbmc/media/weather.rar"
CWeather g_weatherManager;
void CBackgroundWeatherLoader::GetInformation()
{
//if (!g_network.IsAvailable())
// return;
//CWeather *callback = (CWeather *)m_callback;
/*
// Download our weather
CLog::Log(LOGINFO, "WEATHER: Downloading weather");
XFILE::CFileCurl httpUtil;
CStdString strURL;
CStdString strSetting;
strSetting.Format("weather.areacode%i", callback->GetArea() + 1);
CStdString areaCode(callback->GetAreaCode(g_guiSettings.GetString(strSetting)));
strURL.Format("http://xoap.weather.com/weather/local/%s?cc=*&unit=m&dayf=4&prod=xoap&link=xoap&par=%s&key=%s",
areaCode.c_str(), PARTNER_ID, PARTNER_KEY);
CStdString xml;
if (httpUtil.Get(strURL, xml))
{
CLog::Log(LOGINFO, "WEATHER: Weather download successful");
if (!callback->m_bImagesOkay)
{
CDirectory::Create(WEATHER_BASE_PATH);
if (WEATHER_USE_ZIP)
g_ZipManager.ExtractArchive(WEATHER_SOURCE_FILE, WEATHER_BASE_PATH);
else if (WEATHER_USE_RAR)
g_RarManager.ExtractArchive(WEATHER_SOURCE_FILE, WEATHER_BASE_PATH);
callback->m_bImagesOkay = true;
}
callback->LoadWeather(xml);
}
else
CLog::Log(LOGERROR, "WEATHER: Weather download failed!");
*/
}
CWeather::CWeather(void) : CInfoLoader("weather")
{
m_bImagesOkay = false;
Reset();
}
......
{
}
void CWeather::GetString(const TiXmlElement* pRootElement, const CStdString& strTagName, char* szValue, const CStdString& strDefaultValue)
{
strcpy(szValue, "");
const TiXmlNode *pChild = pRootElement->FirstChild(strTagName.c_str());
if (pChild && pChild->FirstChild())
{
CStdString strValue = pChild->FirstChild()->Value();
if (strValue.size() )
{
if (strValue != "-")
strcpy(szValue, strValue.c_str());
}
}
if (strlen(szValue) == 0)
{
strcpy(szValue, strDefaultValue.c_str());
}
}
void CWeather::GetInteger(const TiXmlElement* pRootElement, const CStdString& strTagName, int& iValue)
{
if (!XMLUtils::GetInt(pRootElement, strTagName.c_str(), iValue))
iValue = 0;
}
void CWeather::LocalizeOverviewToken(char *szToken, bool bAppendSpace)
{
// NOTE: This routine is case-sensitive. Reason is std::less<CStdString> uses a case-sensitive
// < operator. Thus, some tokens may have to be duplicated in strings.xml (see drizzle vs Drizzle).
CStdString strLocStr = "";
CStdString token = szToken;
if (!token.IsEmpty())
{
ilocalizedTokens i;
i = m_localizedTokens.find(token);
if (i != m_localizedTokens.end())
{
strLocStr = g_localizeStrings.Get(i->second);
}
}
if (strLocStr == "")
strLocStr = szToken; //if not found, let fallback
if (bAppendSpace)
strLocStr += " "; //append space if applicable
strcpy(szToken, strLocStr.c_str());
}
void CWeather::LocalizeOverview(char *szStr)
{
char loc[256];
char szToken[256];
int intOffset = 0;
char *pnt = NULL;
memset(loc, '\0', sizeof(loc));
while ((pnt = strstr(szStr + intOffset, " ")) != NULL)
{
//get the length of this token (everything before pnt)
int iTokenLen = (int)(strlen(szStr) - strlen(pnt) - intOffset);
strncpy(szToken, szStr + intOffset, iTokenLen); //extract the token
szToken[iTokenLen] = '\0'; //stick an end on it
LocalizeOverviewToken(szToken); //localize
strcpy(loc + strlen(loc), szToken); //add it to the end of loc
intOffset += iTokenLen + 1; //update offset for next strstr search
}
strncpy(szToken, szStr + intOffset, strlen(szStr) - intOffset); //last word, copy the rest of the string
szToken[strlen(szStr) - intOffset] = '\0'; //stick an end on it
LocalizeOverviewToken(szToken); //localize
strcpy(loc + strlen(loc), szToken); //add it to the end of loc
strcpy(szStr, loc); //copy loc over the original input string
}
// input param must be kmh
int CWeather::ConvertSpeed(int curSpeed)
{
switch (g_langInfo.GetSpeedUnit())
{
case CLangInfo::SPEED_UNIT_KMH:
break;
case CLangInfo::SPEED_UNIT_MPS:
curSpeed=(int)(curSpeed * (1000.0 / 3600.0) + 0.5);
break;
case CLangInfo::SPEED_UNIT_MPH:
curSpeed=(int)(curSpeed / (8.0 / 5.0));
break;
case CLangInfo::SPEED_UNIT_MPMIN:
curSpeed=(int)(curSpeed * (1000.0 / 3600.0) + 0.5*60);
break;
case CLangInfo::SPEED_UNIT_FTH:
curSpeed=(int)(curSpeed * 3280.8398888889f);
break;
case CLangInfo::SPEED_UNIT_FTMIN:
curSpeed=(int)(curSpeed * 54.6805555556f);
break;
case CLangInfo::SPEED_UNIT_FTS:
curSpeed=(int)(curSpeed * 0.911344f);
break;
case CLangInfo::SPEED_UNIT_KTS:
curSpeed=(int)(curSpeed * 0.5399568f);
break;
case CLangInfo::SPEED_UNIT_INCHPS:
curSpeed=(int)(curSpeed * 10.9361388889f);
break;
case CLangInfo::SPEED_UNIT_YARDPS:
curSpeed=(int)(curSpeed * 0.3037814722f);
break;
case CLangInfo::SPEED_UNIT_FPF:
curSpeed=(int)(curSpeed * 1670.25f);
break;
case CLangInfo::SPEED_UNIT_BEAUFORT:
{
float knot=(float)curSpeed * 0.5399568f; // to kts first
if(knot<=1.0) curSpeed=0;
if(knot>1.0 && knot<3.5) curSpeed=1;
if(knot>=3.5 && knot<6.5) curSpeed=2;
if(knot>=6.5 && knot<10.5) curSpeed=3;
if(knot>=10.5 && knot<16.5) curSpeed=4;
if(knot>=16.5 && knot<21.5) curSpeed=5;
if(knot>=21.5 && knot<27.5) curSpeed=6;
if(knot>=27.5 && knot<33.5) curSpeed=7;
if(knot>=33.5 && knot<40.5) curSpeed=8;
if(knot>=40.5 && knot<47.5) curSpeed=9;
if(knot>=47.5 && knot<55.5) curSpeed=10;
if(knot>=55.5 && knot<63.5) curSpeed=11;
if(knot>=63.5 && knot<74.5) curSpeed=12;
if(knot>=74.5 && knot<80.5) curSpeed=13;
if(knot>=80.5 && knot<89.5) curSpeed=14;
if(knot>=89.5) curSpeed=15;
}
break;
default:
assert(false);
}
return curSpeed;
}
bool CWeather::LoadWeather(const CStdString &weatherXML)
{
int iTmpInt;
char iTmpStr[256];
SYSTEMTIME time;
GetLocalTime(&time); //used when deciding what weather to grab for today
// Load in our tokens if necessary
if (!m_localizedTokens.size())
LoadLocalizedToken();
// load the xml file
TiXmlDocument xmlDoc;
if (!xmlDoc.Parse(weatherXML))
{
CLog::Log(LOGERROR, "WEATHER: Unable to get data - invalid XML");
return false;
}
TiXmlElement *pRootElement = xmlDoc.RootElement();
if (!pRootElement)
{
CLog::Log(LOGERROR, "WEATHER: Unable to get data - invalid XML");
return false;
}
//if root element is 'error' display the error message
if (strcmp(pRootElement->Value(), "error") == 0)
{
char szCheckError[256];
GetString(pRootElement, "err", szCheckError, "Unknown Error"); //grab the error string
CLog::Log(LOGERROR, "WEATHER: Unable to get data: %s", szCheckError);
return false;
}
// location
TiXmlElement *pElement = pRootElement->FirstChildElement("loc");
if (pElement)
{
GetString(pElement, "dnam", m_szLocation[m_iCurWeather], "");
}
//current weather
pElement = pRootElement->FirstChildElement("cc");
if (pElement)
{
// Use the local date/time the file is parsed...
CDateTime time=CDateTime::GetCurrentDateTime();
CStdString strDateTime=time.GetAsLocalizedDateTime(false, false);
strcpy(m_szLastUpdateTime, strDateTime.c_str());
// ...and not the date/time from weather.com
//GetString(pElement, "lsup", m_szLastUpdateTime, "");
GetString(pElement, "icon", iTmpStr, ""); //string cause i've seen it return N/A
if (strcmp(iTmpStr, "N/A") == 0)
{
sprintf(m_szCurrentIcon, "%s128x128/na.png", WEATHER_BASE_PATH);
}
else
sprintf(m_szCurrentIcon, "%s128x128/%s.png", WEATHER_BASE_PATH, iTmpStr);
GetString(pElement, "t", m_szCurrentConditions, ""); //current condition
LocalizeOverview(m_szCurrentConditions);
GetInteger(pElement, "tmp", iTmpInt); //current temp
CTemperature temp=CTemperature::CreateFromCelsius(iTmpInt);
sprintf(m_szCurrentTemperature, "%2.0f", temp.ToLocale());
GetInteger(pElement, "flik", iTmpInt); //current 'Feels Like'
CTemperature tempFlik=CTemperature::CreateFromCelsius(iTmpInt);
sprintf(m_szCurrentFeelsLike, "%2.0f", tempFlik.ToLocale());
TiXmlElement *pNestElement = pElement->FirstChildElement("wind"); //current wind
if (pNestElement)
{
GetInteger(pNestElement, "s", iTmpInt); //current wind strength
iTmpInt = ConvertSpeed(iTmpInt); //convert speed if needed
GetString(pNestElement, "t", iTmpStr, "N"); //current wind direction
//From <dir eg NW> at <speed> km/h g_localizeStrings.Get(407)
//This is a bit untidy, but i'm fed up with localization and string formats :)
CStdString szWindFrom = g_localizeStrings.Get(407);
CStdString szWindAt = g_localizeStrings.Get(408);
CStdString szCalm = g_localizeStrings.Get(1410);
// get speed unit
char szUnitSpeed[5];
strncpy(szUnitSpeed, g_langInfo.GetSpeedUnitString().c_str(), 5);
szUnitSpeed[4] = '\0';
if (strcmp(iTmpStr,"CALM") == 0)
sprintf(m_szCurrentWind, "%s", szCalm.c_str());
else
sprintf(m_szCurrentWind, "%s %s %s %i %s",
szWindFrom.GetBuffer(szWindFrom.GetLength()), iTmpStr,
szWindAt.GetBuffer(szWindAt.GetLength()), iTmpInt, szUnitSpeed);
}
GetInteger(pElement, "hmid", iTmpInt); //current humidity
sprintf(m_szCurrentHumidity, "%i%%", iTmpInt);
pNestElement = pElement->FirstChildElement("uv"); //current UV index
if (pNestElement)
{
GetInteger(pNestElement, "i", iTmpInt);
GetString(pNestElement, "t", iTmpStr, "");
LocalizeOverviewToken(iTmpStr, false);
sprintf(m_szCurrentUVIndex, "%i %s", iTmpInt, iTmpStr);
}
GetInteger(pElement, "dewp", iTmpInt); //current dew point
CTemperature dewPoint=CTemperature::CreateFromCelsius(iTmpInt);
sprintf(m_szCurrentDewPoint, "%2.0f", dewPoint.ToLocale());
}
//future forcast
pElement = pRootElement->FirstChildElement("dayf");
if (pElement)
{
TiXmlElement *pOneDayElement = pElement->FirstChildElement("day");;
if (pOneDayElement)
{
for (int i = 0; i < NUM_DAYS; i++)
{
const char *attr = pOneDayElement->Attribute("t");
if (attr)
{
strcpy(m_dfForcast[i].m_szDay, attr);
LocalizeDay(m_dfForcast[i].m_szDay);
}
GetString(pOneDayElement, "hi", iTmpStr, ""); //string cause i've seen it return N/A
if (strcmp(iTmpStr, "N/A") == 0)
strcpy(m_dfForcast[i].m_szHigh, "");
else
{
CTemperature temp=CTemperature::CreateFromCelsius(atoi(iTmpStr));
sprintf(m_dfForcast[i].m_szHigh, "%2.0f", temp.ToLocale());
}
GetString(pOneDayElement, "low", iTmpStr, "");
if (strcmp(iTmpStr, "N/A") == 0)
strcpy(m_dfForcast[i].m_szHigh, "");
else
{
CTemperature temp=CTemperature::CreateFromCelsius(atoi(iTmpStr));
sprintf(m_dfForcast[i].m_szLow, "%2.0f", temp.ToLocale());
}
TiXmlElement *pDayTimeElement = pOneDayElement->FirstChildElement("part"); //grab the first day/night part (should be day)
if (pDayTimeElement)
{
if (i == 0 && (time.wHour < 7 || time.wHour >= 19)) //weather.com works on a 7am to 7pm basis so grab night if its late in the day
pDayTimeElement = pDayTimeElement->NextSiblingElement("part");
GetString(pDayTimeElement, "icon", iTmpStr, ""); //string cause i've seen it return N/A
if (strcmp(iTmpStr, "N/A") == 0)
sprintf(m_dfForcast[i].m_szIcon, "%s128x128/na.png", WEATHER_BASE_PATH);
else
sprintf(m_dfForcast[i].m_szIcon, "%s128x128/%s.png", WEATHER_BASE_PATH, iTmpStr);
GetString(pDayTimeElement, "t", m_dfForcast[i].m_szOverview, "");
LocalizeOverview(m_dfForcast[i].m_szOverview);
}
pOneDayElement = pOneDayElement->NextSiblingElement("day");
if (!pOneDayElement)
break; // No more days, break out
}
}
}
return true;
}
//convert weather.com day strings into localized string id's
void CWeather::LocalizeDay(char *szDay)
{
CStdString strLocDay;
if (strcmp(szDay, "Monday") == 0) //monday is localized string 11
strLocDay = g_localizeStrings.Get(11);
else if (strcmp(szDay, "Tuesday") == 0)
strLocDay = g_localizeStrings.Get(12);
else if (strcmp(szDay, "Wednesday") == 0)
strLocDay = g_localizeStrings.Get(13);
else if (strcmp(szDay, "Thursday") == 0)
strLocDay = g_localizeStrings.Get(14);
else if (strcmp(szDay, "Friday") == 0)
strLocDay = g_localizeStrings.Get(15);
else if (strcmp(szDay, "Saturday") == 0)
strLocDay = g_localizeStrings.Get(16);
else if (strcmp(szDay, "Sunday") == 0)
strLocDay = g_localizeStrings.Get(17);
else
strLocDay = "";
strcpy(szDay, strLocDay.GetBuffer(strLocDay.GetLength()));
}
void CWeather::LoadLocalizedToken()
{
// We load the english strings in to get our tokens
CStdString strLanguagePath = "special://xbmc/language/English/strings.xml";
TiXmlDocument xmlDoc;
if (!xmlDoc.LoadFile(strLanguagePath) || !xmlDoc.RootElement())
{
CLog::Log(LOGERROR, "Weather: unable to load %s: %s at line %d", strLanguagePath.c_str(), xmlDoc.ErrorDesc(), xmlDoc.ErrorRow());
return;
}
CStdString strEncoding;
XMLUtils::GetEncoding(&xmlDoc, strEncoding);
TiXmlElement* pRootElement = xmlDoc.RootElement();
if (pRootElement->Value() != CStdString("strings"))
return;
const TiXmlElement *pChild = pRootElement->FirstChildElement();
while (pChild)
{
CStdString strValue = pChild->Value();
if (strValue == "string")
{ // Load new style language file with id as attribute
const char* attrId = pChild->Attribute("id");
if (attrId && !pChild->NoChildren())
{
int id = atoi(attrId);
if ((LOCALIZED_TOKEN_FIRSTID <= id && id <= LOCALIZED_TOKEN_LASTID) ||
(LOCALIZED_TOKEN_FIRSTID2 <= id && id <= LOCALIZED_TOKEN_LASTID2))
{
CStdString utf8Label;
if (strEncoding.IsEmpty()) // Is language file utf8?
utf8Label=pChild->FirstChild()->Value();
else
g_charsetConverter.stringCharsetToUtf8(strEncoding, pChild->FirstChild()->Value(), utf8Label);
if (!utf8Label.IsEmpty())
m_localizedTokens.insert(make_pair(utf8Label, id));
}
}
}
pChild = pChild->NextSiblingElement();
}
}
bool CWeather::GetSearchResults(const CStdString &strSearch, CStdString &strResult)
{
// Check to see if the user entered a weather.com code
if (strSearch.size() == 8)
{
strResult = "";
int i = 0;
for (i = 0; i < 4; ++i)
{
strResult += toupper(strSearch[i]);
if (!isalpha(strSearch[i]))
break;
}
if (i == 4)
{
for ( ; i < 8; ++i)
{
strResult += strSearch[i];
if (!isdigit(strSearch[i]))
break;
}
if (i == 8)
{
return true; // match
}
}
// no match, wipe string
strResult = "";
}
CGUIDialogSelect *pDlgSelect = (CGUIDialogSelect*)g_windowManager.GetWindow(WINDOW_DIALOG_SELECT);
CGUIDialogProgress *pDlgProgress = (CGUIDialogProgress*)g_windowManager.GetWindow(WINDOW_DIALOG_PROGRESS);
//do the download
CStdString strURL;
CStdString strXML;
XFILE::CFileCurl httpUtil;
if (pDlgProgress)
{
pDlgProgress->SetHeading(410); //"Accessing Weather.com"
pDlgProgress->SetLine(0, 194); //"Searching"
pDlgProgress->SetLine(1, strSearch);
pDlgProgress->SetLine(2, "");
pDlgProgress->StartModal();
pDlgProgress->Progress();
}
strURL.Format("http://xoap.weather.com/search/search?where=%s", strSearch);
if (!httpUtil.Get(strURL, strXML))
{
if (pDlgProgress)
pDlgProgress->Close();
return false;
}
//some select dialog init stuff
if (!pDlgSelect)
{
if (pDlgProgress)
pDlgProgress->Close();
return false;
}
pDlgSelect->SetHeading(396); //"Select Location"
pDlgSelect->Reset();
///////////////////////////////
// load the xml file
///////////////////////////////
TiXmlDocument xmlDoc;
xmlDoc.Parse(strXML.c_str());
if (xmlDoc.Error())
return false;
TiXmlElement *pRootElement = xmlDoc.RootElement();
if (pRootElement)
{
CStdString strItemTmp;
TiXmlElement *pElement = pRootElement->FirstChildElement("loc");
while (pElement)
{
if (!pElement->NoChildren())
{
strItemTmp.Format("%s - %s", pElement->Attribute("id"), pElement->FirstChild()->Value());
pDlgSelect->Add(strItemTmp);
}
pElement = pElement->NextSiblingElement("loc");
}
}
if (pDlgProgress)
pDlgProgress->Close();
pDlgSelect->EnableButton(TRUE);
pDlgSelect->SetButtonLabel(222); //'Cancel' button returns to weather settings
pDlgSelect->DoModal();
if (pDlgSelect->GetSelectedLabel() < 0)
{
if (pDlgSelect->IsButtonPressed())
{
pDlgSelect->Close(); //close the select dialog and return to weather settings
return true;
}
}
//copy the selected code into the settings
if (pDlgSelect->GetSelectedLabel() >= 0)
strResult = pDlgSelect->GetSelectedLabelText();
if (pDlgProgress)
pDlgProgress->Close();
return true;
}
const char *CWeather::BusyInfo(int info)
{
if (info == WEATHER_IMAGE_CURRENT_ICON)
{
sprintf(m_szNAIcon,"%s128x128/na.png", WEATHER_BASE_PATH);
return m_szNAIcon;
}
return CInfoLoader::BusyInfo(info);
}
const char *CWeather::TranslateInfo(int info)
{
if (info == WEATHER_LABEL_CURRENT_COND) return m_szCurrentConditions;
else if (info == WEATHER_IMAGE_CURRENT_ICON) return m_szCurrentIcon;
else if (info == WEATHER_LABEL_CURRENT_TEMP) return m_szCurrentTemperature;
else if (info == WEATHER_LABEL_CURRENT_FEEL) return m_szCurrentFeelsLike;
else if (info == WEATHER_LABEL_CURRENT_UVID) return m_szCurrentUVIndex;
else if (info == WEATHER_LABEL_CURRENT_WIND) return m_szCurrentWind;
else if (info == WEATHER_LABEL_CURRENT_DEWP) return m_szCurrentDewPoint;
else if (info == WEATHER_LABEL_CURRENT_HUMI) return m_szCurrentHumidity;
else if (info == WEATHER_LABEL_LOCATION) return m_szLocation[m_iCurWeather];
else if (info == WEATHER_LABEL_LOCATION) return m_szCurrentLocation;
return "";
}
DWORD CWeather::TimeToNextRefreshInMs()
{ // 15 minutes
return 15 * 60 * 1000;
{ // 10 minutes
return 10 * 60 * 1000;
}
CStdString CWeather::GetAreaCity(const CStdString &codeAndCity) const
{
CStdString areaCode(codeAndCity);
int pos = areaCode.Find(" - ");
if (pos >= 0)
areaCode = areaCode.Mid(pos + 3);
return areaCode;
}
CStdString CWeather::GetAreaCode(const CStdString &codeAndCity) const
{
CStdString areaCode(codeAndCity);
int pos = areaCode.Find(" - ");
if (pos >= 0)
areaCode = areaCode.Left(pos);
return areaCode;
}
char *CWeather::GetLocation(int iLocation)
{
if (strlen(m_szLocation[iLocation]) == 0)
......
void CWeather::Reset()
{
strcpy(m_szLastUpdateTime, "");
strcpy(m_szLastUpdateTime, "false");
strcpy(m_szCurrentIcon,"");
strcpy(m_szCurrentConditions, "");
strcpy(m_szCurrentTemperature, "");
strcpy(m_szCurrentFeelsLike, "");
strcpy(m_szCurrentLocation, "");
strcpy(m_szCurrentWind, "");
strcpy(m_szCurrentHumidity, "");
strcpy(m_szCurrentUVIndex, "");
strcpy(m_szCurrentDewPoint, "");
//loop here as well
for (int i = 0; i < NUM_DAYS; i++)
{
strcat(m_dfForcast[i].m_szIcon,"");
strcpy(m_dfForcast[i].m_szOverview, "");
strcpy(m_dfForcast[i].m_szDay, "");
strcpy(m_dfForcast[i].m_szHigh, "");
strcpy(m_dfForcast[i].m_szLow, "");
}
for (int i = 0; i < MAX_LOCATION; i++)
{
strcpy(m_szLocation[i], "");
......
{
// call GetInfo() to make sure that we actually start up
GetInfo(0);
return (0 != *m_szLastUpdateTime);
SetInfo();
return (strcmp(m_szLastUpdateTime, "true") == 0);
}
void CWeather::SetInfo()
{
if (strcmp(m_szLastUpdateTime, "false") == 0 || strcmp(m_szLastUpdateTime, "") == 0)
{
CGUIWindow *window = g_windowManager.GetWindow(WINDOW_WEATHER);
if (window)
{
// set these so existing weather infolabels don't break
strcpy(m_szLastUpdateTime, ((CGUIMediaWindow*)window)->GetProperty("Weather.IsFetched").c_str());
strcpy(m_szCurrentIcon, ((CGUIMediaWindow*)window)->GetProperty("Current.ConditionIcon").c_str());
strcpy(m_szCurrentConditions, ((CGUIMediaWindow*)window)->GetProperty("Current.Condition").c_str());
strcpy(m_szCurrentTemperature, ((CGUIMediaWindow*)window)->GetProperty("Current.Condition").c_str());
strcpy(m_szCurrentLocation, ((CGUIMediaWindow*)window)->GetProperty("Location").c_str());
}
}
}
xbmc/utils/Weather.h (working copy)
#include "InfoLoader.h"
class TiXmlElement;
#define WEATHER_LABEL_LOCATION 10
#define WEATHER_IMAGE_CURRENT_ICON 21
#define WEATHER_LABEL_CURRENT_COND 22
#define WEATHER_LABEL_CURRENT_TEMP 23
#define WEATHER_LABEL_CURRENT_FEEL 24
#define WEATHER_LABEL_CURRENT_UVID 25
#define WEATHER_LABEL_CURRENT_WIND 26
#define WEATHER_LABEL_CURRENT_DEWP 27
#define WEATHER_LABEL_CURRENT_HUMI 28
struct day_forcast
{
char m_szIcon[256];
char m_szOverview[256];
char m_szDay[20];
char m_szHigh[15];
char m_szLow[15];
};
#define NUM_DAYS 4
class CBackgroundWeatherLoader : public CBackgroundLoader
{
public:
CBackgroundWeatherLoader(CInfoLoader *pCallback) : CBackgroundLoader(pCallback) {};
protected:
virtual void GetInformation();
};
class CWeather : public CInfoLoader
......
public:
CWeather(void);
virtual ~CWeather(void);
static bool GetSearchResults(const CStdString &strSearch, CStdString &strResult);
bool LoadWeather(const CStdString& strWeatherFile); //parse strWeatherFile
char *GetLocation(int iLocation);
char *GetLastUpdateTime() { return m_szLastUpdateTime; };
bool IsFetched();
void Reset();
void SetArea(int iArea) { m_iCurWeather = iArea; };
int GetArea() const { return m_iCurWeather; };
CStdString GetAreaCode(const CStdString &codeAndCity) const;
CStdString GetAreaCity(const CStdString &codeAndCity) const;
unsigned int GetMaxLocations();
void SetInfo();
day_forcast m_dfForcast[NUM_DAYS];
bool m_bImagesOkay;
protected:
virtual const char *TranslateInfo(int info);
virtual const char *BusyInfo(int info);
virtual DWORD TimeToNextRefreshInMs();
void GetString(const TiXmlElement* pRootElement, const CStdString& strTagName, char* szValue, const CStdString& strDefaultValue);
void GetInteger(const TiXmlElement* pRootElement, const CStdString& strTagName, int& iValue);
void LocalizeOverview(char *szStr);
void LocalizeOverviewToken(char *szStr, bool bAppendSpace = true);
void LocalizeDay(char *szDay);
void LoadLocalizedToken();
int ConvertSpeed(int speed);
std::map<CStdString, int> m_localizedTokens;
typedef std::map<CStdString, int>::const_iterator ilocalizedTokens;
char m_szLocation[10][100];
// Last updated
......
char m_szCurrentIcon[256];
char m_szCurrentConditions[256];
char m_szCurrentTemperature[10];
char m_szCurrentFeelsLike[10];
char m_szCurrentUVIndex[10];
char m_szCurrentWind[256];
char m_szCurrentDewPoint[10];
char m_szCurrentHumidity[10];
char m_szBusyString[256];
char m_szNAIcon[256];
char m_szCurrentLocation[256];
unsigned int m_iCurWeather;
int m_MaxLocations;
(6-6/13)