From: Kim Kibum Date: Fri, 8 Jun 2012 05:53:59 +0000 (+0900) Subject: apply FSL(Flora Software License) X-Git-Tag: accepted/2.0/20130307.022704~24 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=bed963b6c4431be5d3ce04131683172cc43675ea;p=profile%2Fivi%2Fdownload-provider.git apply FSL(Flora Software License) --- diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 0000000..39c8a0e --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,122 @@ +# +# Copyright (c) Samsung Electronics Co., Ltd. All rights reserved. +# + +CMAKE_MINIMUM_REQUIRED(VERSION 2.6) +PROJECT(download-provider C CXX) + +SET(SRCS + src/main.cpp + src/download-provider-event.cpp + src/download-provider-network.cpp + src/download-provider-view.cpp + src/download-provider-viewItem.cpp + src/download-provider-items.cpp + src/download-provider-item.cpp + src/download-provider-downloadItem.cpp + src/download-provider-downloadRequest.cpp + src/download-provider-util.cpp + src/download-provider-history-db.cpp + src/download-provider-dateTime.cpp + src/download-provider-network.cpp +) + +SET(VENDOR "tizen") +SET(PACKAGE ${PROJECT_NAME}) +SET(PKGNAME "org.${VENDOR}.${PACKAGE}") +SET(PREFIX ${CMAKE_INSTALL_PREFIX}) +SET(BINDIR "${PREFIX}/bin") +SET(RESDIR "${PREFIX}/res") +SET(IMAGEDIR "${RESDIR}/images") +SET(DATADIR "${PREFIX}/data") +SET(DBDATADIR "${PREFIX}/data/db") +SET(LOCALEDIR "${RESDIR}/locale") +SET(ICONDIR "${RESDIR}/icons/default/small") +SET(HISTORYDB ".download-history.db") + +IF("${CMAKE_BUILD_TYPE}" STREQUAL "") + SET(CMAKE_BUILD_TYPE "Release") +ENDIF("${CMAKE_BUILD_TYPE}" STREQUAL "") +MESSAGE("Build type: ${CMAKE_BUILD_TYPE}") + +INCLUDE_DIRECTORIES(${CMAKE_SOURCE_DIR}/src/include) + +INCLUDE(FindPkgConfig) +pkg_check_modules(pkgs REQUIRED + capi-system-runtime-info + capi-appfw-application + appsvc + libdownload-agent + elementary + aul + ecore-x + vconf + bundle + evas + ecore + ecore-input + edje + icu-i18n + xdgmime + eina + ) + +FIND_LIBRARY(LIB_DL dl) + +FIND_PROGRAM(UNAME NAMES uname) +EXEC_PROGRAM("${UNAME}" ARGS "-m" OUTPUT_VARIABLE "ARCH") + +FOREACH(flag ${pkgs_CFLAGS}) + SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} ${flag}") +ENDFOREACH(flag) +FOREACH(flag ${pkgs_include_CFLAGS}) + SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} ${flag}") +ENDFOREACH(flag) + +MESSAGE("ARCH: ${ARCH}") +MESSAGE("LIB_DL: ${LIB_DL}") + +SET(CMAKE_C_FLAGS "${INC_FLAGS}${CMAKE_C_FLAGS} ${EXTRA_CFLAGS} -Wall") +#SET(CMAKE_C_FLAGS_DEBUG "$[CMAKE_C_FLAGS_DEBUG} -O0 -g") +#SET(CMAKE_C_FLAGS_RELEASE "${CMAKE_C_FLAGS_RELEASE} -O2") +SET(CMAKE_CXX_FLAGS "${INC_FLAGS} ${CMAKE_CXX_FLAGS} ${EXTRA_CFLAGS} -Wall") +SET(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -O0 -g -Wall") +SET(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE} -O2") + +IF("${ARCH}" MATCHES "^arm.*") + ADD_DEFINITIONS("-DTARGET") + SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fpie") + SET(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE} -mabi=aapcs-linux -mfpu=vfp -mfloat-abi=softfp") + SET(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -pie") +ENDIF("${ARCH}" MATCHES "^arm.*") + +SET(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -Wl,--as-needed -Wl,--hash-style=both") + +ADD_DEFINITIONS("-DVENDOR=\"${VENDOR}\"") +ADD_DEFINITIONS("-DPACKAGE=\"${PACKAGE}\"") +ADD_DEFINITIONS("-DPACKAGE_NAME=\"${PKGNAME}\"") +ADD_DEFINITIONS("-DPREFIX=\"${PREFIX}\"") +ADD_DEFINITIONS("-DRESDIR=\"${RESDIR}\"") +ADD_DEFINITIONS("-DIMAGEDIR=\"${IMAGEDIR}\"") +ADD_DEFINITIONS("-DDATADIR=\"${DATADIR}\"") +ADD_DEFINITIONS("-DDBDATADIR=\"${DBDATADIR}\"") +ADD_DEFINITIONS("-DLOCALEDIR=\"${LOCALEDIR}\"") +ADD_DEFINITIONS("-DICONDIR=\"${ICONDIR}\"") +ADD_DEFINITIONS("-DHISTORYDB=\"${HISTORYDB}\"") + +ADD_EXECUTABLE(${PROJECT_NAME} ${SRCS}) +TARGET_LINK_LIBRARIES(${PROJECT_NAME} ${pkgs_LDFLAGS} ${LIB_DL}) + +INSTALL(TARGETS ${PROJECT_NAME} DESTINATION ${BINDIR}) + +# install desktop file & icon +CONFIGURE_FILE(${CMAKE_SOURCE_DIR}/res/${PKGNAME}.desktop.in ${CMAKE_BINARY_DIR}/${PKGNAME}.desktop) +INSTALL(DIRECTORY DESTINATION ${DATADIR}) +INSTALL(DIRECTORY DESTINATION ${DBDATADIR}) +INSTALL(FILES ${CMAKE_BINARY_DIR}/${PKGNAME}.desktop DESTINATION /opt/share/applications) +INSTALL(FILES ${CMAKE_SOURCE_DIR}/res/${PKGNAME}.png DESTINATION ${ICONDIR}) +INSTALL(DIRECTORY ${CMAKE_SOURCE_DIR}/res/images DESTINATION ${RESDIR}) + +# i18n +ADD_SUBDIRECTORY(po) + diff --git a/INSTALL b/INSTALL new file mode 100644 index 0000000..3f81c54 --- /dev/null +++ b/INSTALL @@ -0,0 +1,33 @@ +1. make the build directory + + ex) + + $ mkdir build + + +2. change the working directory to the build directory + + ex) + + $ cd build + + +3. run 'cmake' + + $ cmake ${SOURCE_DIR} -DCMAKE_INSTALL_PREFIX=/opt/apps/@@PKGNAME@@ + + ex) + + $ cmake .. -DCMAKE_INSTALL_PREFIX=/opt/apps/@@PKGNAME@@ + + or + + $ cmake .. + + +4. make & make install + + ex) + + $ make -j 2 && make install + diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..7ccb5b5 --- /dev/null +++ b/LICENSE @@ -0,0 +1,75 @@ +Flora License + +Version 1.0, May, 2012 + +http://www.tizenopensource.org/license + +TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + +1. Definitions. + +"License" shall mean the terms and conditions for use, reproduction, and distribution as defined by Sections 1 through 9 of this document. + +"Licensor" shall mean the copyright owner or entity authorized by the copyright owner that is granting the License. + +"Legal Entity" shall mean the union of the acting entity and all other entities that control, are controlled by, or are under common control with that entity. For the purposes of this definition, "control" means (i) the power, direct or indirect, to cause the direction or management of such entity, whether by contract or otherwise, or (ii) ownership of fifty percent (50%) or more of the outstanding shares, or (iii) beneficial ownership of such entity. + +"You" (or "Your") shall mean an individual or Legal Entity exercising permissions granted by this License. + +"Source" form shall mean the preferred form for making modifications, including but not limited to software source code, documentation source, and configuration files. + +"Object" form shall mean any form resulting from mechanical transformation or translation of a Source form, including but not limited to compiled object code, generated documentation, and conversions to other media types. + +"Work" shall mean the work of authorship, whether in Source or Object form, made available under the License, as indicated by a copyright notice that is included in or attached to the work (an example is provided in the Appendix below). + +"Derivative Works" shall mean any work, whether in Source or Object form, that is based on (or derived from) the Work and for which the editorial revisions, annotations, elaborations, or other modifications represent, as a whole, an original work of authorship. For the purposes of this License, Derivative Works shall not include works that remain separable from, or merely link (or bind by name) to the interfaces of, the Work and Derivative Works thereof. + +"Contribution" shall mean any work of authorship, including the original version of the Work and any modifications or additions to that Work or Derivative Works thereof, that is intentionally submitted to Licensor for inclusion in the Work by the copyright owner or by an individual or Legal Entity authorized to submit on behalf of the copyright owner. For the purposes of this definition, "submitted" means any form of electronic, verbal, or written communication sent to the Licensor or its representatives, including but not limited to communication on electronic mailing lists, source code control systems, and issue tracking systems that are managed by, or on behalf of, the Licensor for the purpose of discussing and improving the Work, but excluding communication that is conspicuously marked or otherwise designated in writing by the copyright owner as "Not a Contribution." + +"Contributor" shall mean Licensor and any individual or Legal Entity on behalf of whom a Contribution has been received by Licensor and subsequently incorporated within the Work. + +"Tizen Certified Platform" shall mean a software platform that complies with the standards set forth in the Compatibility Definition Document and passes the Compatibility Test Suite as defined from time to time by the Tizen Technical Steering Group and certified by the Tizen Association or its designated agent. + +2. Grant of Copyright License. Subject to the terms and conditions of this License, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, irrevocable copyright license to reproduce, prepare Derivative Works of, publicly display, publicly perform, sublicense, and distribute the Work and such Derivative Works in Source or Object form. + +3. Grant of Patent License. Subject to the terms and conditions of this License, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, irrevocable (except as stated in this section) patent license to make, have made, use, offer to sell, sell, import, and otherwise transfer the Work solely as incorporated into a Tizen Certified Platform, where such license applies only to those patent claims licensable by such Contributor that are necessarily infringed by their Contribution(s) alone or by combination of their Contribution(s) with the Work solely as incorporated into a Tizen Certified Platform to which such Contribution(s) was submitted. If You institute patent litigation against any entity (including a cross-claim or counterclaim in a lawsuit) alleging that the Work or a Contribution incorporated within the Work constitutes direct or contributory patent infringement, then any patent licenses granted to You under this License for that Work shall terminate as of the date such litigation is filed. + +4. Redistribution. You may reproduce and distribute copies of the Work or Derivative Works thereof pursuant to the copyright license above, in any medium, with or without modifications, and in Source or Object form, provided that You meet the following conditions: + + 1. You must give any other recipients of the Work or Derivative Works a copy of this License; and + + 2. You must cause any modified files to carry prominent notices stating that You changed the files; and + + 3. You must retain, in the Source form of any Derivative Works that You distribute, all copyright, patent, trademark, and attribution notices from the Source form of the Work, excluding those notices that do not pertain to any part of the Derivative Works; and + + 4. If the Work includes a "NOTICE" text file as part of its distribution, then any Derivative Works that You distribute must include a readable copy of the attribution notices contained within such NOTICE file, excluding those notices that do not pertain to any part of the Derivative Works, in at least one of the following places: within a NOTICE text file distributed as part of the Derivative Works; within the Source form or documentation, if provided along with the Derivative Works; or, within a display generated by the Derivative Works, if and wherever such third-party notices normally appear. The contents of the NOTICE file are for informational purposes only and do not modify the License. You may add Your own attribution notices within Derivative Works that You distribute, alongside or as an addendum to the NOTICE text from the Work, provided that such additional attribution notices cannot be construed as modifying the License. You may add Your own copyright statement to Your modifications and may provide additional or different license terms and conditions for use, reproduction, or distribution of Your modifications, or for any such Derivative Works as a whole, provided Your use, reproduction, and distribution of the Work otherwise complies with the conditions stated in this License. + +5. Submission of Contributions. Unless You explicitly state otherwise, any Contribution intentionally submitted for inclusion in the Work by You to the Licensor shall be under the terms and conditions of this License, without any additional terms or conditions. Notwithstanding the above, nothing herein shall supersede or modify the terms of any separate license agreement you may have executed with Licensor regarding such Contributions. + +6. Trademarks. This License does not grant permission to use the trade names, trademarks, service marks, or product names of the Licensor, except as required for reasonable and customary use in describing the origin of the Work and reproducing the content of the NOTICE file. + +7. Disclaimer of Warranty. Unless required by applicable law or agreed to in writing, Licensor provides the Work (and each Contributor provides its Contributions) on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied, including, without limitation, any warranties or conditions of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A PARTICULAR PURPOSE. You are solely responsible for determining the appropriateness of using or redistributing the Work and assume any risks associated with Your exercise of permissions under this License. + +8. Limitation of Liability. In no event and under no legal theory, whether in tort (including negligence), contract, or otherwise, unless required by applicable law (such as deliberate and grossly negligent acts) or agreed to in writing, shall any Contributor be liable to You for damages, including any direct, indirect, special, incidental, or consequential damages of any character arising as a result of this License or out of the use or inability to use the Work (including but not limited to damages for loss of goodwill, work stoppage, computer failure or malfunction, or any and all other commercial damages or losses), even if such Contributor has been advised of the possibility of such damages. + +9. Accepting Warranty or Additional Liability. While redistributing the Work or Derivative Works thereof, You may choose to offer, and charge a fee for, acceptance of support, warranty, indemnity, or other liability obligations and/or rights consistent with this License. However, in accepting such obligations, You may act only on Your own behalf and on Your sole responsibility, not on behalf of any other Contributor, and only if You agree to indemnify, defend, and hold each Contributor harmless for any liability incurred by, or claims asserted against, such Contributor by reason of your accepting any such warranty or additional liability. + +END OF TERMS AND CONDITIONS + +APPENDIX: How to apply the Flora License to your work + +To apply the Flora License to your work, attach the following boilerplate notice, with the fields enclosed by brackets "[]" replaced with your own identifying information. (Don't include the brackets!) The text should be enclosed in the appropriate comment syntax for the file format. We also recommend that a file or class name and description of purpose be included on the same "printed page" as the copyright notice for easier identification within third-party archives. + + Copyright [yyyy] [name of copyright owner] + + Licensed under the Flora License, Version 1.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.tizenopensource.org/license + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. diff --git a/NOTICE b/NOTICE new file mode 100644 index 0000000..1a82fd9 --- /dev/null +++ b/NOTICE @@ -0,0 +1 @@ +Copyright (c) Samsung Electronics Co., Ltd. All rights reserved. diff --git a/debian/changelog b/debian/changelog new file mode 100644 index 0000000..928eadd --- /dev/null +++ b/debian/changelog @@ -0,0 +1,8 @@ +download-provider (1.0.0-0) unstable; urgency=low + * Git: pkgs/d/download-provider + * Tag: download-provider_1.0.0-0 + + * Tizen release. + + -- Jungki Kwak Fri, 16 Mar 2012 14:41:48 +0900 + diff --git a/debian/compat b/debian/compat new file mode 100644 index 0000000..7ed6ff8 --- /dev/null +++ b/debian/compat @@ -0,0 +1 @@ +5 diff --git a/debian/control b/debian/control new file mode 100644 index 0000000..2d00f93 --- /dev/null +++ b/debian/control @@ -0,0 +1,17 @@ +Source: download-provider +Section: misc +Priority: extra +Maintainer: Jungki Kwak , Keunsoon Lee , InBum Chang +Build-Depends: debhelper (>= 5), libdownload-agent-dev, libelm-dev, libeina-dev, libaul-1-dev, libecore-dev, libvconf-dev, libbundle-dev, libicu-dev, libxdgmime-dev, capi-system-runtime-info-dev, capi-appfw-application-dev, libappsvc-dev +Standards-Version: 0.1.0 + +Package: org.tizen.download-provider +Architecture: any +Depends: ${shlibs:Depends}, ${misc:Depends}, libicu +Description: Application for support of the content download + +Package: org.tizen.download-provider-dbg +Section: debug +Architecture: any +Depends: org.tizen.download-provider (= ${Source-Version}) +Description: Application for support of the content download (unstripped) diff --git a/debian/dirs b/debian/dirs new file mode 100644 index 0000000..ca882bb --- /dev/null +++ b/debian/dirs @@ -0,0 +1,2 @@ +usr/bin +usr/sbin diff --git a/debian/org.tizen.download-provider.install.in b/debian/org.tizen.download-provider.install.in new file mode 100644 index 0000000..e95ca2a --- /dev/null +++ b/debian/org.tizen.download-provider.install.in @@ -0,0 +1,4 @@ +@PREFIX@/bin/* +@PREFIX@/data +@PREFIX@/res/* +opt/share/applications/* diff --git a/debian/org.tizen.download-provider.postinst b/debian/org.tizen.download-provider.postinst new file mode 100644 index 0000000..8183086 --- /dev/null +++ b/debian/org.tizen.download-provider.postinst @@ -0,0 +1,26 @@ +#!/bin/sh + +#### Download History #### +if [ ${USER} == "root" ] +then + # Change file owner + chown -R 5000:5000 /opt/apps/org.tizen.download-provider/data +fi + +if [ ! -f /opt/apps/org.tizen.download-provider/data/db/.download-history.db ]; +then + sqlite3 /opt/apps/org.tizen.download-provider/data/db/.download-history.db 'PRAGMA journal_mode=PERSIST; + create table history(id integer primary key autoincrement, historyid integer, downloadtype integer, contenttype integer, state integer, err integer, name, vendor, path, url, cookie, date datetime);' +fi + +if [ ${USER} == "root" ] +then +# Change file owner + chown -R 5000:5000 /opt/apps/org.tizen.download-provider/data + chown :6002 /opt/apps/org.tizen.download-provider/data/db/.download-history.db + chown :6002 /opt/apps/org.tizen.download-provider/data/db/.download-history.db-journal + chmod 660 /opt/apps/org.tizen.download-provider/data/db/.download-history.db + chmod 660 /opt/apps/org.tizen.download-provider/data/db/.download-history.db-journal +fi + + diff --git a/debian/rules b/debian/rules new file mode 100755 index 0000000..bbf1a0c --- /dev/null +++ b/debian/rules @@ -0,0 +1,116 @@ +#!/usr/bin/make -f +# -*- makefile -*- +# Sample debian/rules that uses debhelper. +# This file was originally written by Joey Hess and Craig Small. +# As a special exception, when this file is copied by dh-make into a +# dh-make output file, you may use that output file without restriction. +# This special exception was added by Craig Small in version 0.37 of dh-make. + +# Uncomment this to turn on verbose mode. +#export DH_VERBOSE=1 + +CFLAGS ?= -Wall -g +LDFLAGS ?= +PREFIX ?= /opt/apps/org.tizen.download-provider +RESDIR ?= /opt/apps/org.tizen.download-provider/res +DATADIR ?= /opt/apps/org.tizen.download-provider/data + +ifneq (,$(findstring noopt,$(DEB_BUILD_OPTIONS))) + CFLAGS += -O0 + CXXFLAGS += -O0 +else + CFLAGS += -O2 + CXXFLAGS += -O2 +endif + +LDFLAGS += -Wl,--rpath=$(PREFIX)/lib -Wl,--as-needed + +CMAKE_BUILD_DIR ?= $(CURDIR)/cmake_build_tmp + +configure: configure-stamp +configure-stamp: + dh_testdir + # Add here commands to configure the package. + mkdir -p $(CMAKE_BUILD_DIR) && cd $(CMAKE_BUILD_DIR) && \ + CFLAGS="$(CFLAGS)" LDFLAGS="$(LDFLAGS)" cmake .. -DCMAKE_INSTALL_PREFIX="$(PREFIX)" + + touch configure-stamp + +build: build-stamp + +build-stamp: configure-stamp + dh_testdir + + # Add here commands to compile the package. + cd $(CMAKE_BUILD_DIR) && $(MAKE) + + for f in `find $(CURDIR)/debian/ -name "*.in"`; do \ + cat $$f > $${f%.in}; \ + sed -i -e "s#@PREFIX@#$(PREFIX)#g" $${f%.in}; \ + sed -i -e "s#@RESDIR@#$(RESDIR)#g" $${f%.in}; \ + sed -i -e "s#@DATADIR@#$(DATADIR)#g" $${f%.in}; \ + done + + touch $@ + +clean: + dh_testdir + dh_testroot + rm -f build-stamp configure-stamp + + # Add here commands to clean up after the build process. + rm -rf $(CMAKE_BUILD_DIR) + + for f in `find $(CURDIR)/debian/ -name "*.in"`; do \ + rm -f $${f%.in}; \ + done + + dh_clean + +install: build + dh_testdir + dh_testroot + dh_clean -k +# dh_installdirs + + # Add here commands to install the package into debian/wavplayer. + cd $(CMAKE_BUILD_DIR) && $(MAKE) DESTDIR=$(CURDIR)/debian/tmp install + + +# Build architecture-independent files here. +binary-indep: build install +# We have nothing to do by default. + +# Build architecture-dependent files here. +binary-arch: build install + dh_testdir + dh_testroot +# dh_installchangelogs +# dh_installdocs +# dh_installexamples + dh_install --sourcedir=debian/tmp +# dh_installmenu +# dh_installdebconf +# dh_installlogrotate +# dh_installemacsen +# dh_installpam +# dh_installmime +# dh_python +# dh_installinit +# dh_installcron +# dh_installinfo + dh_installman + dh_link + dh_strip --dbg-package=org.tizen.download-provider-dbg + dh_compress + dh_fixperms +# dh_perl + dh_makeshlibs + dh_installdeb + dh_shlibdeps + dh_gencontrol + dh_md5sums + dh_builddeb + +binary: binary-indep binary-arch +.PHONY: build clean binary-indep binary-arch binary install configure diff --git a/packaging/org.tizen.download-provider.spec b/packaging/org.tizen.download-provider.spec new file mode 100644 index 0000000..32aaf76 --- /dev/null +++ b/packaging/org.tizen.download-provider.spec @@ -0,0 +1,71 @@ + +Name: org.tizen.download-provider +Summary: Application for support of the content download +Version: 1.0.0 +Release: 1 +Group: TO_BE_FILLED_IN +License: Flora Software License +URL: N/A +Source0: %{name}-%{version}.tar.gz +BuildRequires: pkgconfig(capi-system-runtime-info) +BuildRequires: pkgconfig(capi-appfw-application) +BuildRequires: pkgconfig(appsvc) +BuildRequires: pkgconfig(libdownload-agent) +BuildRequires: pkgconfig(elementary) +BuildRequires: pkgconfig(aul) +BuildRequires: pkgconfig(ecore) +BuildRequires: pkgconfig(vconf) +BuildRequires: pkgconfig(bundle) +BuildRequires: pkgconfig(xdgmime) +BuildRequires: pkgconfig(notification) +BuildRequires: pkgconfig(icu-i18n) +BuildRequires: cmake +BuildRequires: gettext-devel +BuildRequires: expat-devel +BuildRequires: edje-tools + +%description +Application for support of the content download + +%prep +%setup -q + +%build +cmake . -DCMAKE_INSTALL_PREFIX="/opt/apps/org.tizen.download-provider" + +make %{?jobs:-j%jobs} + +%install +rm -rf %{buildroot} +%make_install + +%post +#### Download History #### +if [ ${USER} == "root" ] +then + # Change file owner + chown -R 5000:5000 /opt/apps/org.tizen.download-provider/data +fi + +if [ ! -f /opt/apps/org.tizen.download-provider/data/db/.download-history.db ]; +then + sqlite3 /opt/apps/org.tizen.download-provider/data/db/.download-history.db 'PRAGMA journal_mode=PERSIST; + create table history(id integer primary key autoincrement, historyid integer, downloadtype integer, contenttype integer, state integer, err integer, name, vendor, path, url, cookie, date datetime);' +fi + +if [ ${USER} == "root" ] +then + chown -R 5000:5000 /opt/apps/org.tizen.download-provider/data + chown :6002 /opt/apps/org.tizen.download-provider/data/db/.download-history.db + chown :6002 /opt/apps/org.tizen.download-provider/data/db/.download-history.db-journal + chmod 660 /opt/apps/org.tizen.download-provider/data/db/.download-history.db + chmod 660 /opt/apps/org.tizen.download-provider/data/db/.download-history.db-journal +fi + +%files +%defattr(-,root,root,-) +/opt/apps/org.tizen.download-provider/bin/* +/opt/apps/org.tizen.download-provider/data +/opt/apps/org.tizen.download-provider/res/* +/opt/share/applications/* + diff --git a/po/CMakeLists.txt b/po/CMakeLists.txt new file mode 100644 index 0000000..0197f3d --- /dev/null +++ b/po/CMakeLists.txt @@ -0,0 +1,24 @@ +# for i18n + +SET(POFILES en.po de_DE.po el_GR.po es_ES.po fr_FR.po it_IT.po ja_JP.po ko_KR.po nl_NL.po pt_PT.po ru_RU.po tr_TR.po zh_CN.po zh_HK.po zh_TW.po) + +SET(MSGFMT "/usr/bin/msgfmt") + +FOREACH(pofile ${POFILES}) + SET(pofile ${CMAKE_CURRENT_SOURCE_DIR}/${pofile}) + MESSAGE("PO: ${pofile}") + GET_FILENAME_COMPONENT(absPofile ${pofile} ABSOLUTE) + GET_FILENAME_COMPONENT(lang ${absPofile} NAME_WE) + SET(moFile ${CMAKE_CURRENT_BINARY_DIR}/${lang}.mo) + ADD_CUSTOM_COMMAND( + OUTPUT ${moFile} + COMMAND ${MSGFMT} -o ${moFile} ${absPofile} + DEPENDS ${absPofile} + ) + INSTALL(FILES ${moFile} + DESTINATION ${LOCALEDIR}/${lang}/LC_MESSAGES RENAME ${PROJECT_NAME}.mo) + SET(moFiles ${moFiles} ${moFile}) +ENDFOREACH(pofile) + +MESSAGE(".mo files: ${moFiles}") +ADD_CUSTOM_TARGET(po ALL DEPENDS ${moFiles}) diff --git a/po/POTFILES.in.in b/po/POTFILES.in.in new file mode 100644 index 0000000..bcb7f1f --- /dev/null +++ b/po/POTFILES.in.in @@ -0,0 +1,2 @@ +# List of source files containing translatable strings. +@@APPNAME@@.c diff --git a/po/csv2po b/po/csv2po new file mode 100644 index 0000000..0c9a53a Binary files /dev/null and b/po/csv2po differ diff --git a/po/de_DE.po b/po/de_DE.po new file mode 100644 index 0000000..4532322 --- /dev/null +++ b/po/de_DE.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "Installation gescheitert" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "Benachrichtigung..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "Verarbeitung abgeschlossen" + +msgid "IDS_BR_SK_RETRY" +msgstr "Ern. vers." + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "Download-Manager" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "Ungültiger Descriptor" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "Keine Downloads" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "Abgeschlossen" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "Datei kann nicht geöffnet werden" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "Herunterladen?" + diff --git a/po/el_GR.po b/po/el_GR.po new file mode 100644 index 0000000..1eaacb2 --- /dev/null +++ b/po/el_GR.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "Αποτυχία εγκατάστασης" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "Ειδοποίηση..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "Ολοκλήρωση επεξεργασίας" + +msgid "IDS_BR_SK_RETRY" +msgstr "Επανάληψη" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "Διαχείριση λήψεων" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "Μη έγκυρη περιγραφή" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "Δεν υπάρχουν λήψεις" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "Ολοκληρώθηκε" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "Δεν είναι δυνατό το άνοιγμα αρχείου" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "Λήψη;" + diff --git a/po/en.po b/po/en.po new file mode 100644 index 0000000..c7289d7 --- /dev/null +++ b/po/en.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "Installation failed" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "Notifying..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "Processing completed" + +msgid "IDS_BR_SK_RETRY" +msgstr "Retry" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "Download manager" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "Invalid descriptor" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "No downloads" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "Complete" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "Unable to open file" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "Download?" + diff --git a/po/es_ES.po b/po/es_ES.po new file mode 100644 index 0000000..1434878 --- /dev/null +++ b/po/es_ES.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "Fallo en la instalación" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "Notificando..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "Procesamiento finalizado" + +msgid "IDS_BR_SK_RETRY" +msgstr "Reint." + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "Administrador de descarga" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "Descriptor no válido" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "Sin descargas" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "Completo" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "No se puede abrir el archivo" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "¿Descargar?" + diff --git a/po/fr_FR.po b/po/fr_FR.po new file mode 100644 index 0000000..e408209 --- /dev/null +++ b/po/fr_FR.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "Echec de l'installation" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "Notification..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "Traitement terminé" + +msgid "IDS_BR_SK_RETRY" +msgstr "Réessayer" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "Gestionnaire de téléchargement" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "Descripteur non valide" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "Aucun téléchargement" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "OK" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "Impossible d'ouvrir le fichier" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "Télécharger ?" + diff --git a/po/it_IT.po b/po/it_IT.po new file mode 100644 index 0000000..5ce8183 --- /dev/null +++ b/po/it_IT.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "Installazione fallita" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "Notifica in corso..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "Elaborazione completata" + +msgid "IDS_BR_SK_RETRY" +msgstr "Riprova" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "Gestione download" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "Descrittore non valido" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "Nessun download" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "Completo" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "Impossibile aprire file" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "Scaricare?" + diff --git a/po/ja_JP.po b/po/ja_JP.po new file mode 100644 index 0000000..467255b --- /dev/null +++ b/po/ja_JP.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "インストール​失敗" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "通知中..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "処理​が​完了​しました" + +msgid "IDS_BR_SK_RETRY" +msgstr "再接続" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "ダウンロードマネージャー" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "識別子​が​無効​です" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr " ダウンロード​なし" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "完了" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "ファイル​を​開く​こと​が​できません" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "ダウンロードしますか?" + diff --git a/po/ko_KR.po b/po/ko_KR.po new file mode 100644 index 0000000..d29d75b --- /dev/null +++ b/po/ko_KR.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "설치하지 못하였습니다" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "알림 준비 중..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "완료되었습니다" + +msgid "IDS_BR_SK_RETRY" +msgstr "재시도" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "다운로드 관리자" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "설명이 바르지 않습니다" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "다운로드가 없습니다" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "완료" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "파일을 열 수 없습니다" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "다운로드할까요?" + diff --git a/po/nl_NL.po b/po/nl_NL.po new file mode 100644 index 0000000..fb28efe --- /dev/null +++ b/po/nl_NL.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "Installatie mislukt" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "Melden..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "Verwerken voltooid" + +msgid "IDS_BR_SK_RETRY" +msgstr "Opnieuw" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "Downloadmanager" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "Ongeldige descriptor" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "Geen downloads" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "Voltooid" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "Kan bestand niet openen" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "Downloaden?" + diff --git a/po/pt_PT.po b/po/pt_PT.po new file mode 100644 index 0000000..4ea32df --- /dev/null +++ b/po/pt_PT.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "Instalação falhou" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "A notificar..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "Processamento concluído" + +msgid "IDS_BR_SK_RETRY" +msgstr "Repetir" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "Gestor de transferências" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "Descrição inválida" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "Nenhumas transferências" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "Concluída" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "Impossível abrir ficheiro" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "Transferir?" + diff --git a/po/ru_RU.po b/po/ru_RU.po new file mode 100644 index 0000000..bbeb1dd --- /dev/null +++ b/po/ru_RU.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "Сбой установки" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "Уведомление..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "Обработка завершена" + +msgid "IDS_BR_SK_RETRY" +msgstr "Повтор" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "Диспетчер загрузки" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "Неверный дескриптор" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "Нет загрузок" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "Завершено" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "Невозможно открыть файл" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "Загрузить?" + diff --git a/po/tr_TR.po b/po/tr_TR.po new file mode 100644 index 0000000..63f05e2 --- /dev/null +++ b/po/tr_TR.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "Yükleme başarısız" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "Bildiriliyor..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "İşlem tamamlandı" + +msgid "IDS_BR_SK_RETRY" +msgstr "Y.dene" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "İndirme Yöneticisi" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "Geçersiz Tanımlayıcı" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "İndirme yok" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "Tamamlandı" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "Dosyayı açamıyor" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "Yüklensin mi?" + diff --git a/po/update-po.sh.in b/po/update-po.sh.in new file mode 100644 index 0000000..df45634 --- /dev/null +++ b/po/update-po.sh.in @@ -0,0 +1,60 @@ +#!/bin/sh + +PACKAGE=@@APPNAME@@ +SRCROOT=.. +POTFILES=POTFILES.in + +#ALL_LINGUAS= am az be ca cs da de el en_CA en_GB es et fi fr hr hu it ja ko lv mk ml ms nb ne nl pa pl pt pt_BR ru rw sk sl sr sr@Latn sv ta tr uk vi zh_CN zh_TW +ALL_LINGUAS="en_US en_GB ja ko zh_CN" + +XGETTEXT=/usr/bin/xgettext +MSGMERGE=/usr/bin/msgmerge + +echo -n "Make ${PACKAGE}.pot " +if [ ! -e $POTFILES ] ; then + echo "$POTFILES not found" + exit 1 +fi + +$XGETTEXT --default-domain=${PACKAGE} --directory=${SRCROOT} \ + --add-comments --keyword=_ --keyword=N_ --files-from=$POTFILES +if [ $? -ne 0 ]; then + echo "xgettext error" + exit 1 +fi + +if [ ! -f ${PACKAGE}.po ]; then + echo "No such file: ${PACKAGE}.po" + exit 1 +fi + +rm -f ${PACKAGE}.pot && mv ${PACKAGE}.po ${PACKAGE}.pot +echo "done" + +for LANG in $ALL_LINGUAS; do + echo "$LANG : " + + if [ ! -e $LANG.po ] ; then + sed 's/CHARSET/UTF-8/g' ${PACKAGE}.pot > ${LANG}.po + echo "${LANG}.po created" + else + if $MSGMERGE ${LANG}.po ${PACKAGE}.pot -o ${LANG}.new.po ; then + if cmp ${LANG}.po ${LANG}.new.po > /dev/null 2>&1; then + rm -f ${LANG}.new.po + else + if mv -f ${LANG}.new.po ${LANG}.po; then + echo "" + else + echo "msgmerge for $LANG.po failed: cannot move $LANG.new.po to $LANG.po" 1>&2 + rm -f ${LANG}.new.po + exit 1 + fi + fi + else + echo "msgmerge for $LANG failed!" + rm -f ${LANG}.new.po + fi + fi + echo "" +done + diff --git a/po/zh_CN.po b/po/zh_CN.po new file mode 100644 index 0000000..88675f3 --- /dev/null +++ b/po/zh_CN.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "安装失败" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "通知中..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "处理完成" + +msgid "IDS_BR_SK_RETRY" +msgstr "重试" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "下载管理器" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "描述符无效" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "无下载项" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "完成" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "无法打开文件" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "下载?" + diff --git a/po/zh_HK.po b/po/zh_HK.po new file mode 100644 index 0000000..cb6fc1b --- /dev/null +++ b/po/zh_HK.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "安裝失敗" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "正在通知..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "處理完成" + +msgid "IDS_BR_SK_RETRY" +msgstr "重試" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "下載管理員" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "無效描述項" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "無下載項目" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "完成" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "無法開啟檔案" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "要下載嗎?" + diff --git a/po/zh_TW.po b/po/zh_TW.po new file mode 100644 index 0000000..9a9c0f5 --- /dev/null +++ b/po/zh_TW.po @@ -0,0 +1,30 @@ +msgid "IDS_BR_POP_INSTALLATION_FAILED" +msgstr "安裝失敗" + +msgid "IDS_BR_BODY_NOTIFYING_ING" +msgstr "正在通知..." + +msgid "IDS_BR_BODY_PROCESSING_COMPLETED" +msgstr "處理完成" + +msgid "IDS_BR_SK_RETRY" +msgstr "重試" + +msgid "IDS_BR_HEADER_DOWNLOAD_MANAGER" +msgstr "下載管理員" + +msgid "IDS_BR_POP_INVALIDDESCRIPTOR" +msgstr "描述元無效" + +msgid "IDS_DL_BODY_NO_DOWNLOADS" +msgstr "無下載" + +msgid "IDS_EMAIL_BODY_COMPLETE" +msgstr "完成" + +msgid "IDS_BR_POP_UNABLE_TO_OPEN_FILE" +msgstr "無法開啟檔案" + +msgid "IDS_BR_POP_DOWNLOAD_Q" +msgstr "要下載嗎?" + diff --git a/res/images/U06_icon_DRM.png b/res/images/U06_icon_DRM.png new file mode 100644 index 0000000..adb9254 Binary files /dev/null and b/res/images/U06_icon_DRM.png differ diff --git a/res/images/U06_icon_Java.png b/res/images/U06_icon_Java.png new file mode 100644 index 0000000..317be17 Binary files /dev/null and b/res/images/U06_icon_Java.png differ diff --git a/res/images/U06_icon_Unknown.png b/res/images/U06_icon_Unknown.png new file mode 100644 index 0000000..024cfc1 Binary files /dev/null and b/res/images/U06_icon_Unknown.png differ diff --git a/res/images/U06_icon_excel.png b/res/images/U06_icon_excel.png new file mode 100644 index 0000000..2ef1042 Binary files /dev/null and b/res/images/U06_icon_excel.png differ diff --git a/res/images/U06_icon_html.png b/res/images/U06_icon_html.png new file mode 100644 index 0000000..72fed4a Binary files /dev/null and b/res/images/U06_icon_html.png differ diff --git a/res/images/U06_icon_image.png b/res/images/U06_icon_image.png new file mode 100644 index 0000000..5b11f78 Binary files /dev/null and b/res/images/U06_icon_image.png differ diff --git a/res/images/U06_icon_music.png b/res/images/U06_icon_music.png new file mode 100644 index 0000000..12b6cb8 Binary files /dev/null and b/res/images/U06_icon_music.png differ diff --git a/res/images/U06_icon_pdf.png b/res/images/U06_icon_pdf.png new file mode 100644 index 0000000..b99803e Binary files /dev/null and b/res/images/U06_icon_pdf.png differ diff --git a/res/images/U06_icon_ppt.png b/res/images/U06_icon_ppt.png new file mode 100644 index 0000000..60341e3 Binary files /dev/null and b/res/images/U06_icon_ppt.png differ diff --git a/res/images/U06_icon_ringtone.png b/res/images/U06_icon_ringtone.png new file mode 100644 index 0000000..4ea1672 Binary files /dev/null and b/res/images/U06_icon_ringtone.png differ diff --git a/res/images/U06_icon_text.png b/res/images/U06_icon_text.png new file mode 100644 index 0000000..b156b91 Binary files /dev/null and b/res/images/U06_icon_text.png differ diff --git a/res/images/U06_icon_video.png b/res/images/U06_icon_video.png new file mode 100644 index 0000000..0ee8587 Binary files /dev/null and b/res/images/U06_icon_video.png differ diff --git a/res/images/U06_icon_word.png b/res/images/U06_icon_word.png new file mode 100644 index 0000000..96d3e50 Binary files /dev/null and b/res/images/U06_icon_word.png differ diff --git a/res/org.tizen.download-provider.desktop.in b/res/org.tizen.download-provider.desktop.in new file mode 100644 index 0000000..e94bc6c --- /dev/null +++ b/res/org.tizen.download-provider.desktop.in @@ -0,0 +1,12 @@ +Name=Download Provider +Name[en_US]=Download Provider +Exec=/opt/apps/org.tizen.download-provider/bin/download-provider +Icon=icon_default.png +Type=Application +Comment=Download Provider +nodisplay=true +X-TIZEN-TaskManage=false +X-TIZEN-Multiple=false +X-TIZEN-Removable=false +X-TIZEN-SVC= http://tizen.org/appsvc/operation/download|http|NULL;http://tizen.org/appsvc/operation/download|NULL|NULL +Version=0.1.0-0 diff --git a/res/org.tizen.download-provider.png b/res/org.tizen.download-provider.png new file mode 100644 index 0000000..bffa6bb Binary files /dev/null and b/res/org.tizen.download-provider.png differ diff --git a/src/download-provider-dateTime.cpp b/src/download-provider-dateTime.cpp new file mode 100644 index 0000000..8f6edd3 --- /dev/null +++ b/src/download-provider-dateTime.cpp @@ -0,0 +1,218 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-dateTime.cpp + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief data and utility APIs for Date and Time + */ + +#include "runtime_info.h" +#include "download-provider-dateTime.h" + +#define MAX_SKELETON_BUFFER_LEN 8 +#define MAX_PATTERN_BUFFER_LEN 128 + +DateGroup::DateGroup() + : count(0) + , type(DATETIME::DATE_TYPE_NONE) + , m_glGroupItem(NULL) +{ +} + +DateGroup::~DateGroup() +{ +} + +void DateGroup::initData() +{ + count = 0; + m_glGroupItem = NULL; +} + +DateUtil::DateUtil() + : m_todayStandardTime(0) + , dateShortFormat(NULL) + , dateMediumFormat(NULL) + , dateFullFormat(NULL) + , timeFormat12H(NULL) + , timeFormat24H(NULL) +{ +} + +DateUtil::~DateUtil() +{ + deinitLocaleData(); +} + +void DateUtil::deinitLocaleData() +{ + if (dateShortFormat) + udat_close(dateShortFormat); + if (dateMediumFormat) + udat_close(dateMediumFormat); + if (dateFullFormat) + udat_close(dateFullFormat); + if (timeFormat12H) + udat_close(timeFormat12H); + if (timeFormat24H) + udat_close(timeFormat24H); + dateShortFormat = NULL; + dateMediumFormat = NULL; + dateFullFormat = NULL; + timeFormat12H = NULL; + timeFormat24H = NULL; +} + +int DateUtil::getDiffDaysFromToday() +{ + time_t now = time(NULL); + DP_LOGD("todayStandardTime[%ld]", m_todayStandardTime); + if (m_todayStandardTime == 0) + return 0; + else + return getDiffDays(now, m_todayStandardTime); +} + +int DateUtil::getDiffDays(time_t nowTime,time_t refTime) +{ + int diffDays = 0; + int nowYear = 0; + int nowYday = 0; + int refYday = 0; + int refYear = 0; + struct tm *nowDate = localtime(&nowTime); + nowYday = nowDate->tm_yday; + nowYear = nowDate->tm_year; + struct tm *finishedDate = localtime(&refTime); + refYday = finishedDate->tm_yday; + refYear = finishedDate->tm_year; + diffDays = nowYday - refYday; + /*DP_LOGD("refDate[%d/%d/%d]refTime[%ld]yday[%d]", + (finishedDate->tm_year + 1900), (finishedDate->tm_mon + 1), + finishedDate->tm_mday, refTime, refYday);*/ + if ((nowYear-refYear)>0 && diffDays < 0) { + int year = nowDate->tm_year; + diffDays = diffDays + 365; + /* leap year */ + if ((year%4 == 0 && year%100 != 0) || year%400 == 0) + diffDays++; + } + DP_LOGD("diffDays[%d]",diffDays); + return diffDays; +} + +UDateFormat *DateUtil::getBestPattern(const char *patternStr, + UDateTimePatternGenerator *generator, const char *locale) +{ + UDateFormat *format = NULL; + UChar customSkeleton[MAX_SKELETON_BUFFER_LEN] = {0,}; + UChar bestPattern[MAX_PATTERN_BUFFER_LEN] = {0,}; + UErrorCode status = U_ZERO_ERROR; + int32_t patternLen = 0; + + if (patternStr) { + u_uastrncpy(customSkeleton, patternStr, strlen(patternStr)); + patternLen = udatpg_getBestPattern(generator, customSkeleton, + u_strlen(customSkeleton), bestPattern, MAX_PATTERN_BUFFER_LEN, + &status); + DP_LOGD("udatpg_getBestPattern status[%d] bestPattern[%s]", status, + bestPattern); + if (patternLen < 1) { + format = udat_open(UDAT_SHORT, UDAT_NONE, locale, NULL, -1, + NULL, -1, &status); + return format; + } + } + format = udat_open(UDAT_IGNORE, UDAT_NONE, locale, NULL, -1, + bestPattern, -1, &status); + return format; +} + +void DateUtil::updateLocale() +{ + UDateTimePatternGenerator *generator = NULL; + UErrorCode status = U_ZERO_ERROR; + const char *locale = NULL; + + DP_LOGD_FUNC(); + + deinitLocaleData(); + + uloc_setDefault(getenv("LC_TIME"), &status); + DP_LOGD("uloc_setDefault status[%d]",status); + + locale = uloc_getDefault(); + generator = udatpg_open(locale,&status); + DP_LOGD("udatpg_open status[%d]",status); + + timeFormat12H = getBestPattern("hm", generator, locale); + timeFormat24H = getBestPattern("Hm", generator, locale); + + dateShortFormat = udat_open(UDAT_NONE, UDAT_SHORT, locale, NULL, -1, NULL, + -1, &status); + dateMediumFormat = udat_open(UDAT_NONE, UDAT_MEDIUM, locale, NULL, -1, NULL, + -1, &status); + dateFullFormat = getBestPattern("yMMMEEEd", generator, locale); + udatpg_close(generator); +} + +void DateUtil::getDateStr(int style, double time, string &outBuf) +{ + UDateFormat *format = NULL; + UErrorCode status = U_ZERO_ERROR; + UChar str[MAX_BUF_LEN] = {0,}; + bool value = false; + + DP_LOGD_FUNC(); + switch (style) { + case LOCALE_STYLE::TIME: + if (runtime_info_get_value_bool( + RUNTIME_INFO_KEY_24HOUR_CLOCK_FORMAT_ENABLED,&value) != 0) { + DP_LOGE("runtime_info_get_value_bool is failed"); + format = timeFormat12H; + } else { + if (value) + format = timeFormat24H; + else + format = timeFormat12H; + } + break; + case LOCALE_STYLE::SHORT_DATE: + format = dateShortFormat; + break; + case LOCALE_STYLE::MEDIUM_DATE: + format = dateMediumFormat; + break; + case LOCALE_STYLE::FULL_DATE: + format = dateFullFormat; + break; + default : + DP_LOGE("Critical: cannot enter here"); + format = timeFormat12H; + } + if (format) { + char tempBuf[MAX_BUF_LEN] = {0,}; + udat_format(format, time, str, MAX_BUF_LEN - 1, NULL, &status); + DP_LOGD("udat_format : status[%d]", status); + u_austrncpy(tempBuf, str, MAX_BUF_LEN-1); + outBuf = string(tempBuf); + } else { + DP_LOGE("Critical: fail to get time value"); + outBuf = string(S_("IDS_COM_POP_ERROR")); + } +} + diff --git a/src/download-provider-downloadItem.cpp b/src/download-provider-downloadItem.cpp new file mode 100644 index 0000000..de3df50 --- /dev/null +++ b/src/download-provider-downloadItem.cpp @@ -0,0 +1,493 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-downloadItem.cpp + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief download item class for interface of download agent + */ + +#include "download-provider-downloadItem.h" + +#include "download-provider-common.h" +#include +#include + +/* Download Agent CallBacks */ +static void __notify_cb(user_notify_info_t *notify_info, void *user_data); +static void __update_download_info_cb(user_download_info_t *download_info, void *user_data); +static void __get_dd_info_cb(user_dd_info_t *dd_info, void *user_data); + +static Ecore_Pipe *ecore_pipe = NULL; +static void __ecore_cb_pipe_update(void *data, void *buffer, unsigned int nbyte); + +namespace DA_CB { +enum TYPE { + NOTIFY = 1, + UPDATE, + DD_INFO +}; +} + +class CbData { +public: + CbData() {} + ~CbData() {} + + void updateDownloadItem(); + + inline void setType(DA_CB::TYPE type) { m_type = type; } + inline void setUserData(void *userData) { m_userData = userData; } + inline void setDownloadId(int id) { m_da_req_id = id; } + inline void setReceivedFileSize(unsigned long int size) { m_receivedFileSize = size; } + inline void setFileSize(unsigned long int size) { m_fileSize = size; } + inline void setFilePath(const char *path) { if (path) m_filePath = path; } + inline void setRegisteredFilePath(const char *path) { if (path) m_registeredFilePath = path; } + inline void setMimeType(const char *mime) { m_mimeType = mime; } + inline void setState(da_state state) { m_da_state = state; } + inline void setErrorCode(int err) { m_da_error = err; } + inline void setIsMidletInstalled(bool b) { m_isMidletInstalled = b; } + inline void setIsJad(bool b) { m_isJad = b;} + inline void setContentName(const char *name) { m_contentName = name; } + inline void setVendorName(const char *name) { m_vendorName = name; } + +private: + DA_CB::TYPE m_type; + void *m_userData; + da_handle_t m_da_req_id; + da_state m_da_state; + int m_da_error; + unsigned long int m_receivedFileSize; + unsigned long int m_fileSize; + string m_filePath; + string m_registeredFilePath; + string m_mimeType; + bool m_isMidletInstalled; + bool m_isJad; + string m_contentName; + string m_vendorName; +}; + +struct pipe_data_t { + CbData *cbData; +}; + +DownloadEngine::DownloadEngine() +{ +} + +DownloadEngine::~DownloadEngine() +{ + DP_LOG_FUNC(); +} + +void DownloadEngine::initEngine(void) +{ + da_client_cb_t da_cb = { + __notify_cb, /* da_notify_cb */ + __get_dd_info_cb, /* da_send_dd_info_cb */ + __update_download_info_cb, /* da_update_download_info_cb */ + NULL /* da_go_to_next_url_cb */ + }; + + int da_ret = da_init(&da_cb, DA_DOWNLOAD_MANAGING_METHOD_AUTO); + if (DA_RESULT_OK == da_ret) { + ecore_pipe = ecore_pipe_add(__ecore_cb_pipe_update, NULL); + } +} + +void DownloadEngine::deinitEngine(void) +{ + da_deinit(); + if (ecore_pipe) { + ecore_pipe_del(ecore_pipe); + ecore_pipe = NULL; + } +} + +void CbData::updateDownloadItem() +{ +// DP_LOGD_FUNC(); + + if (!m_userData) { + DP_LOGE("download item is NULL"); + return; + } + + + DownloadItem *downloadItem = static_cast(m_userData); + if (downloadItem->state() == DL_ITEM::FAILED) { + DP_LOGE("download item is already failed"); + return; + } + + switch(m_type) { + case DA_CB::NOTIFY: + { + DP_LOGD("DA_CB::NOTIFY"); + downloadItem->setDownloadId(m_da_req_id); + DL_ITEM::STATE dl_state = downloadItem->_convert_da_state_to_download_state(m_da_state); + DP_LOG("DL_ITEM::STATE [%d]", dl_state); + //if (dl_state != DL_ITEM::IGNORE) + if (dl_state == DL_ITEM::IGNORE) + return; + downloadItem->setState(dl_state); + + if (dl_state == DL_ITEM::FAILED) + downloadItem->setErrorCode(downloadItem->_convert_da_error(m_da_error)); + } + break; + + case DA_CB::UPDATE: + DP_LOGD("DA_CB::UPDATE"); + DP_LOGD("DA_CB::UPDATE state[%d] receivedFileSize[%d]", downloadItem->state(), m_receivedFileSize); +// downloadItem->setDownloadId(m_da_req_id); + downloadItem->setState(DL_ITEM::UPDATING); + downloadItem->setReceivedFileSize(m_receivedFileSize); + downloadItem->setFileSize(m_fileSize); + + if (!m_mimeType.empty()) + downloadItem->setMimeType(m_mimeType); + + if (!m_filePath.empty()) + downloadItem->setFilePath(m_filePath); + + if (!m_registeredFilePath.empty()) { + DP_LOGD("registeredFilePath[%s]", m_registeredFilePath.c_str()); + downloadItem->setRegisteredFilePath(m_registeredFilePath); + } + break; + + case DA_CB::DD_INFO: + DP_LOG("DA_CB::DD_INFO"); + downloadItem->setDownloadId(m_da_req_id); + downloadItem->setFileSize(m_fileSize); + downloadItem->setIsMidletInstalled(m_isMidletInstalled); + if (m_isJad) + downloadItem->setDownloadType(DL_TYPE::MIDP_DOWNLOAD); + else + downloadItem->setDownloadType(DL_TYPE::OMA_DOWNLOAD); + downloadItem->setContentName(m_contentName); + downloadItem->setVendorName(m_vendorName); + downloadItem->setState(DL_ITEM::WAITING_CONFIRM); + break; + + default: + break; + } + + downloadItem->notify(); +} + +void __ecore_cb_pipe_update(void *data, void *buffer, unsigned int nbyte) +{ +// DP_LOGD_FUNC(); + + if (!buffer) + return; + pipe_data_t *pipe_data = static_cast(buffer); + CbData *cbData = pipe_data->cbData; + if (!cbData) + return; + + cbData->updateDownloadItem(); + delete cbData; +} + +void __notify_cb(user_notify_info_t *notify_info, void* user_data) +{ + DP_LOGD_FUNC(); + + if (!notify_info || !user_data) + return; + + DP_LOGD("__notify_cb: id[%d] state[%d] err[%d]", notify_info->da_dl_req_id, notify_info->state, notify_info->err); + + CbData *cbData = new CbData(); + cbData->setType(DA_CB::NOTIFY); + cbData->setDownloadId(notify_info->da_dl_req_id); + cbData->setUserData(user_data); + cbData->setState(notify_info->state); + cbData->setErrorCode(notify_info->err); + + pipe_data_t pipe_data; + pipe_data.cbData = cbData; + ecore_pipe_write(ecore_pipe, &pipe_data, sizeof(pipe_data_t)); +} + +void __update_download_info_cb(user_download_info_t *download_info, void *user_data) +{ +// DP_LOGD_FUNC(); + + if (!download_info || !user_data) + return; + + CbData *cbData = new CbData(); + cbData->setType(DA_CB::UPDATE); + cbData->setDownloadId(download_info->da_dl_req_id); + cbData->setUserData(user_data); + cbData->setFileSize(download_info->file_size); + cbData->setReceivedFileSize(download_info->total_received_size); + +// DP_LOGD("tmp path [%s] path [%s] type [%s]", download_info->tmp_saved_path, download_info->saved_path, download_info->file_type); + DownloadItem *item = static_cast(user_data); + if(download_info->file_type && item->mimeType().empty()) + cbData->setMimeType(download_info->file_type); + + if(download_info->tmp_saved_path && item->filePath().empty()) + cbData->setFilePath(download_info->tmp_saved_path); + + if(download_info->saved_path && item->registeredFilePath().empty()) + cbData->setRegisteredFilePath(download_info->saved_path); + + pipe_data_t pipe_data; + pipe_data.cbData = cbData; + ecore_pipe_write(ecore_pipe, &pipe_data, sizeof(pipe_data_t)); +} + +void __get_dd_info_cb(user_dd_info_t *dd_info, void *user_data) +{ + DP_LOGD_FUNC(); + + if (!dd_info || !user_data) + return; + + CbData *cbData = new CbData(); + cbData->setType(DA_CB::DD_INFO); + cbData->setDownloadId(dd_info->da_dl_req_id); + cbData->setUserData(user_data); + cbData->setIsMidletInstalled(dd_info->is_installed); + cbData->setIsJad(dd_info->is_jad); + cbData->setFileSize(dd_info->size); + + if (dd_info->name) + cbData->setContentName(dd_info->name); + if (dd_info->vendor) + cbData->setVendorName(dd_info->vendor); + if (dd_info->type) + cbData->setMimeType(dd_info->type); + + pipe_data_t pipe_data; + pipe_data.cbData = cbData; + ecore_pipe_write(ecore_pipe, &pipe_data, sizeof(pipe_data_t)); +} + +DownloadItem::DownloadItem() + : m_da_req_id(DA_INVALID_ID) + , m_state(DL_ITEM::IGNORE) + , m_errorCode(ERROR::NONE) + , m_receivedFileSize(0) + , m_fileSize(0) + , m_downloadType(DL_TYPE::HTTP_DOWNLOAD) + , m_isMidletInstalled(false) +{ +} + +DownloadItem::DownloadItem(auto_ptr request) + : m_aptr_request(request) + , m_da_req_id(DA_INVALID_ID) + , m_state(DL_ITEM::IGNORE) + , m_errorCode(ERROR::NONE) + , m_receivedFileSize(0) + , m_fileSize(0) + , m_downloadType(DL_TYPE::HTTP_DOWNLOAD) + , m_isMidletInstalled(false) +{ +} + +DownloadItem::~DownloadItem() +{ + DP_LOGD_FUNC(); +} + +void DownloadItem::start(void) +{ + int da_ret = 0; + DP_LOGD_FUNC(); + + if (m_aptr_request->getCookie().empty()) { + da_ret = da_start_download_with_extension( + m_aptr_request->getUrl().c_str(), + &m_da_req_id, + DA_FEATURE_USER_DATA, + static_cast(this), + NULL); + } else { + char *requestHeader[1] = {NULL,}; + int reqHeaderCount = 1; + string reqHeaderStr = string("Cookie:"); + reqHeaderStr.append(m_aptr_request->getCookie().c_str()); + requestHeader[0] = strdup(reqHeaderStr.c_str()); + da_ret = da_start_download_with_extension( + m_aptr_request->getUrl().c_str(), + &m_da_req_id, + DA_FEATURE_REQUEST_HEADER, + requestHeader, + &reqHeaderCount, + DA_FEATURE_USER_DATA, + static_cast(this), + NULL); + if (requestHeader[0]) { + free(requestHeader[0]); + requestHeader[0] = NULL; + } + } + if (da_ret != DA_RESULT_OK) { + m_state = DL_ITEM::FAILED; + m_errorCode = ERROR::ENGINE_FAIL; + notify(); + } +} + +DL_ITEM::STATE DownloadItem::_convert_da_state_to_download_state(int da_state) +{ + switch (da_state) { + case DA_STATE_DOWNLOAD_STARTED: + return DL_ITEM::STARTED; +// case DA_STATE_DOWNLOADING: +// return DL_ITEM::UPDATING; + case DA_STATE_DOWNLOAD_COMPLETE: + return DL_ITEM::COMPLETE_DOWNLOAD; + case DA_STATE_WAITING_USER_CONFIRM: + return DL_ITEM::WAITING_CONFIRM; + case DA_STATE_START_INSTALL_NOTIFY: + return DL_ITEM::INSTALL_NOTIFY; + case DA_STATE_DRM_JOIN_LEAVE_DOMAIN_START: + return DL_ITEM::START_DRM_DOMAIN; + case DA_STATE_DRM_JOIN_LEAVE_DOMAIN_FINISH: + return DL_ITEM::FINISH_DRM_DOMAIN; + case DA_STATE_WAITING_RO: + return DL_ITEM::WAITING_RO; + case DA_STATE_SUSPENDED: + return DL_ITEM::SUSPENDED; + case DA_STATE_RESUMED: + return DL_ITEM::RESUMED; + case DA_STATE_CANCELED: + return DL_ITEM::CANCELED; + case DA_STATE_FINISHED: + return DL_ITEM::FINISHED; + case DA_STATE_FAILED: + return DL_ITEM::FAILED; + case DA_STATE_DOWNLOADING: + case DA_STATE_DONE_INSTALL_NOTIFY: + case DA_STATE_DRM_ROAP_START: + case DA_STATE_DRM_ROAP_FINISH: + default: + return DL_ITEM::IGNORE; + } +} + +ERROR::CODE DownloadItem::_convert_da_error(int da_err) +{ + DP_LOGD("download agent error[%d]", da_err); + + switch (da_err) { + case DA_ERR_NETWORK_FAIL: + case DA_ERR_HTTP_TIMEOUT: + case DA_ERR_UNREACHABLE_SERVER : + return ERROR::NETWORK_FAIL; + + case DA_ERR_INVALID_URL: + return ERROR::INVALID_URL; + + case DA_ERR_DISK_FULL: + return ERROR::NOT_ENOUGH_MEMORY; + + case DA_ERR_FAIL_TO_INSTALL_FILE: + case DA_ERR_DLOPEN_FAIL: + return ERROR::FAIL_TO_INSTALL; + + case DA_ERR_USER_RESPONSE_WAITING_TIME_OUT: + return ERROR::OMA_POPUP_TIME_OUT; + + case DA_ERR_PARSE_FAIL: + return ERROR::FAIL_TO_PARSE_DESCRIPTOR; + + default : + return ERROR::UNKNOWN; + } + +} + +void DownloadItem::cancel() +{ + DP_LOGD("DownloadItem::cancel"); + if (m_state == DL_ITEM::CANCELED) { + DP_LOGD("It is already canceled"); + notify(); + return; + } + int da_ret = da_cancel_download(m_da_req_id); + if (da_ret != DA_RESULT_OK) { + DP_LOGE("Fail to cancel download : reqId[%d] reason[%d]", + m_da_req_id, da_ret); + m_state = DL_ITEM::FAILED; + m_errorCode = ERROR::ENGINE_FAIL; + notify(); + } + return; +} + +void DownloadItem::retry() +{ + DP_LOGD_FUNC(); + m_da_req_id = DA_INVALID_ID; + m_state = DL_ITEM::IGNORE; + m_errorCode = ERROR::NONE; + m_receivedFileSize = 0; + m_fileSize = 0; + m_downloadType = DL_TYPE::HTTP_DOWNLOAD; + m_isMidletInstalled = false; + start(); +} + +bool DownloadItem::sendUserResponse(bool res) +{ + int da_ret = da_send_back_user_confirm(m_da_req_id, res); + if (da_ret != DA_RESULT_OK) { + DP_LOGE("Fail to send back user confirm : reqId[%d] reason[%d]", + m_da_req_id, da_ret); + m_state = DL_ITEM::FAILED; + m_errorCode = ERROR::ENGINE_FAIL; + notify(); + return false; + } + return true; +} + +void DownloadItem::suspend() +{ + int da_ret = DA_RESULT_OK; + da_ret = da_suspend_download(m_da_req_id); + if (da_ret != DA_RESULT_OK) { + DP_LOGE("Fail to suspend download : reqId[%d] err[%d]", m_da_req_id, da_ret); + m_state = DL_ITEM::FAILED; + m_errorCode = ERROR::ENGINE_FAIL; + notify(); + } +} + +void DownloadItem::resume() +{ + int da_ret = DA_RESULT_OK; + da_ret = da_resume_download(m_da_req_id); + if (da_ret != DA_RESULT_OK) { + DP_LOGE("Fail to resume download : reqId[%d] err[%d]", m_da_req_id, da_ret); + m_state = DL_ITEM::FAILED; + m_errorCode = ERROR::ENGINE_FAIL; + notify(); + } +} diff --git a/src/download-provider-downloadRequest.cpp b/src/download-provider-downloadRequest.cpp new file mode 100644 index 0000000..4c1608c --- /dev/null +++ b/src/download-provider-downloadRequest.cpp @@ -0,0 +1,75 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provier-downloadRequest.cpp + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief download request data class + */ +#include "download-provider-downloadRequest.h" + +/*DownloadRequest::DownloadRequest() + : m_url(NULL) + , m_cookie(NULL) +{ +}*/ + +DownloadRequest::DownloadRequest(string url, string cookie) + : m_url(url) + , m_cookie(cookie) +{ +} + +DownloadRequest::DownloadRequest(DownloadRequest &rRequest) +{ + m_url.assign(rRequest.getUrl()); + m_cookie.assign(rRequest.getCookie()); +} + +DownloadRequest::~DownloadRequest() +{ +// DP_LOG_FUNC(); +} + +string &DownloadRequest::getUrl() +{ + return m_url; +} + +string &DownloadRequest::getCookie() +{ + return m_cookie; +} + +bool DownloadRequest::isUrlEmpty() +{ + return m_url.empty(); +} + +bool DownloadRequest::isCookieEmpty() +{ + return m_cookie.empty(); +} + +void DownloadRequest::setUrl(string url) +{ + m_url.assign(url); +} + +void DownloadRequest::setCookie(string cookie) +{ + m_cookie.assign(cookie); +} diff --git a/src/download-provider-event.cpp b/src/download-provider-event.cpp new file mode 100644 index 0000000..1484727 --- /dev/null +++ b/src/download-provider-event.cpp @@ -0,0 +1,91 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-event.cpp + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief download event class for event flow + */ +#include "download-provider-event.h" +#include "download-provider-common.h" + +#include + +void Subject::attach(Observer *o) +{ + _observers.push_back(o); +} + +void Subject::detach(Observer *o) +{ + vector::iterator it; + for(it = _observers.begin() ; it < _observers.end() ; it++) { + if (*it == o) { + _observers.erase(it); + break; + } + } +} + +void Subject::notify(void) +{ + vector::iterator it; + Observer *curObserver; + it = _observers.begin(); + while (it < _observers.end()) { + curObserver = *it; + + DP_LOGD("[%s] Call Update",curObserver->name().c_str()); + (*it)->update(this); + + if (curObserver != *it) + continue; + + it++; + } +} + +void Observer::update(Subject *s) +{ + call(); +} + +//Observer::Observer(updateFunction uf, void *data) +/* For debug */ +Observer::Observer(updateFunction uf, void *data, const char *name) + : m_updateFunction(uf) + , m_userData(data) +{ + observerName = name; +} + +void Observer::set(updateFunction uf, void *data) +{ + m_updateFunction = uf; + m_userData = data; +} + +void Observer::clear(void) +{ + m_updateFunction = 0; + m_userData = 0; +} + +void Observer::call(void) +{ + if (m_updateFunction) + m_updateFunction(m_userData); +} diff --git a/src/download-provider-history-db.cpp b/src/download-provider-history-db.cpp new file mode 100644 index 0000000..7772ac8 --- /dev/null +++ b/src/download-provider-history-db.cpp @@ -0,0 +1,443 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-history-db.cpp + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Manager for a download history DB + */ + +#include +#include "download-provider-common.h" +#include "download-provider-history-db.h" + +#define FINALIZE_ON_ERROR( stmt ) { \ + DP_LOG("SQL error: %d", ret);\ + if (sqlite3_finalize(stmt) != SQLITE_OK)\ + DP_LOGE("sqlite3_finalize is failed.");\ + close();\ + return false; \ +} + +sqlite3 *DownloadHistoryDB::historyDb = NULL; + +DownloadHistoryDB::DownloadHistoryDB() +{ +} + +DownloadHistoryDB::~DownloadHistoryDB() +{ +} + +bool DownloadHistoryDB::open() +{ + int ret = 0; + + DP_LOGD_FUNC(); + + close(); + + ret = db_util_open(DBDATADIR"/"HISTORYDB, &historyDb, + DB_UTIL_REGISTER_HOOK_METHOD); + + if (ret != SQLITE_OK) { + DP_LOGE("open fail"); + db_util_close(historyDb); + historyDb = NULL; + return false; + } + + return isOpen(); +} + +void DownloadHistoryDB::close() +{ + DP_LOGD_FUNC(); + if (historyDb) { + db_util_close(historyDb); + historyDb = NULL; + } +} + +/* FIXME : Hitory entry limitation ?? */ +bool DownloadHistoryDB::addToHistoryDB(Item *item) +{ + int ret = 0; + sqlite3_stmt *stmt = NULL; + const char *name = NULL; + + DP_LOG_FUNC(); + + if (!item) { + DP_LOGE("Item is NULL"); + return false; + } + + if (item->historyId() < 0) { + DP_LOGE("Cannot add to DB. Because historyId is invaild"); + return false; + } + + if (!open()) { + DP_LOGE("historyDB is NULL"); + return false; + } + + const string statement = "insert into history (historyid, downloadtype,\ + contenttype, state, err, name, vendor, path, url, cookie, date) \ + values(?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"; + + ret = sqlite3_prepare_v2(historyDb, statement.c_str(), -1, &stmt, NULL); + + if (ret != SQLITE_OK) + FINALIZE_ON_ERROR(stmt); + /* binding values */ + if (sqlite3_bind_int(stmt, 1, item->historyId()) != SQLITE_OK) + DP_LOGE("sqlite3_bind_int is failed."); + if (sqlite3_bind_int(stmt, 2, item->downloadType()) != SQLITE_OK) + DP_LOGE("sqlite3_bind_int is failed."); + if (sqlite3_bind_int(stmt, 3, item->contentType()) != SQLITE_OK) + DP_LOGE("sqlite3_bind_int is failed."); + if (sqlite3_bind_int(stmt, 4, item->state()) != SQLITE_OK) + DP_LOGE("sqlite3_bind_int is failed."); + if (sqlite3_bind_int(stmt, 5, item->errorCode()) != SQLITE_OK) + DP_LOGE("sqlite3_bind_int is failed."); + if (item->downloadType() == DL_TYPE::MIDP_DOWNLOAD) + name = item->contentName().c_str(); + else + name = item->title().c_str(); + if (sqlite3_bind_text(stmt, 6, name, -1, NULL) != SQLITE_OK) + DP_LOGE("sqlite3_bind_text is failed."); + if (sqlite3_bind_text(stmt, 7, item->vendorName().c_str(), -1, NULL) != + SQLITE_OK) + DP_LOGE("sqlite3_bind_int is failed."); + if (sqlite3_bind_text( + stmt, 8, item->registeredFilePath().c_str(), -1, NULL) != SQLITE_OK) + DP_LOGE("sqlite3_bind_text is failed."); + if (sqlite3_bind_text(stmt, 9, item->url().c_str(), -1, NULL) != SQLITE_OK) + DP_LOGE("sqlite3_bind_text is failed."); + if (sqlite3_bind_text(stmt, 10, item->cookie().c_str(), -1, NULL) != SQLITE_OK) + DP_LOGE("sqlite3_bind_text is failed."); + if (sqlite3_bind_double(stmt, 11, item->finishedTime()) != SQLITE_OK) + DP_LOGE("sqlite3_bind_double is failed."); + ret = sqlite3_step(stmt); + + DP_LOGD("SQL return: %s", (ret == SQLITE_ROW || ret == SQLITE_OK)?"Success":"Fail"); + + close(); + + return ret == SQLITE_DONE; +} + +bool DownloadHistoryDB::getCountOfHistory(int *count) +{ + int ret = 0; + sqlite3_stmt *stmt = NULL; + + DP_LOG_FUNC(); + + if (!open()) { + DP_LOGE("historyDB is NULL"); + return false; + } + ret = sqlite3_prepare_v2(historyDb, "select COUNT(*) from history", -1, &stmt, NULL); + if (ret != SQLITE_OK) + FINALIZE_ON_ERROR(stmt); + + ret = sqlite3_step(stmt); + DP_LOGD("SQL return: %s", (ret == SQLITE_ROW || ret == SQLITE_OK)?"Success":"Fail"); + if (ret == SQLITE_ROW) { + *count = sqlite3_column_int(stmt,0); + DP_LOGD("count[%d]",*count); + } else { + DP_LOGE("SQL query error"); + *count = 0; + } + + if (sqlite3_finalize(stmt) != SQLITE_OK) + DP_LOGE("sqlite3_finalize is failed."); + close(); + return true; +} + +bool DownloadHistoryDB::createRemainedItemsFromHistoryDB(int limit, int offset) +{ + int ret = 0; + stringstream limitStr; + stringstream offsetStr; + sqlite3_stmt *stmt = NULL; + string tmp; + + DP_LOG_FUNC(); + + if (!open()) { + DP_LOGE("historyDB is NULL"); + return false; + } + limitStr << limit; + offsetStr << offset; + + tmp.append("select historyid, downloadtype, contenttype, state, err, "); + tmp.append("name, vendor, path, url, cookie, date from history order by "); + tmp.append("date DESC limit "); + tmp.append(limitStr.str()); + tmp.append(" offset "); + tmp.append(offsetStr.str()); + ret = sqlite3_prepare_v2(historyDb, tmp.c_str(), -1, &stmt, NULL); + if (ret != SQLITE_OK) + FINALIZE_ON_ERROR(stmt); + + for (;;) { + ret = sqlite3_step(stmt); + if (ret == SQLITE_ROW) { + const char *tempStr = NULL; + string arg; + string url; + string cookie; + Item *item = Item::createHistoryItem(); + if (!item) { + DP_LOGE("Fail to create item"); + break; + } + item->setHistoryId(sqlite3_column_int(stmt,0)); + item->setDownloadType((DL_TYPE::TYPE)sqlite3_column_int(stmt,1)); + item->setContentType(sqlite3_column_int(stmt,2)); + item->setState((ITEM::STATE)sqlite3_column_int(stmt,3)); + item->setErrorCode((ERROR::CODE)sqlite3_column_int(stmt,4)); + tempStr = (const char *)(sqlite3_column_text(stmt,5)); + if (tempStr) { + arg = tempStr; + if (item->downloadType() == DL_TYPE::MIDP_DOWNLOAD) + item->setContentName(arg); + item->setTitle(arg); + } + tempStr = (const char *)(sqlite3_column_text(stmt,6)); + if (tempStr) + arg = tempStr; + else + arg = string(); + item->setVendorName(arg); + tempStr = (const char *)(sqlite3_column_text(stmt,7)); + if (tempStr) + arg = tempStr; + else + arg = string(); + item->setRegisteredFilePath(arg); + tempStr = (const char *)(sqlite3_column_text(stmt,8)); + if (tempStr) + url = tempStr; + else + url = string(); + tempStr = (const char *)(sqlite3_column_text(stmt,9)); + if (tempStr) + cookie = tempStr; + else + cookie = string(); + item->setFinishedTime(sqlite3_column_double(stmt,10)); + item->attachHistoryItem(); + item->setRetryData(url, cookie); + } else + break; + } + DP_LOGD("SQL error: %d", ret); + + if (sqlite3_finalize(stmt) != SQLITE_OK) + DP_LOGE("sqlite3_finalize is failed."); + + close(); + + if (ret == SQLITE_DONE || ret == SQLITE_ROW) + return true; + else + return false; +} + +bool DownloadHistoryDB::createItemsFromHistoryDB() +{ + int ret = 0; + sqlite3_stmt *stmt = NULL; + string tmp; + stringstream limitStr; + + DP_LOG_FUNC(); + + if (!open()) { + DP_LOGE("historyDB is NULL"); + return false; + } + limitStr << LOAD_HISTORY_COUNT; + tmp.append("select historyid, downloadtype, contenttype, state, err, "); + tmp.append("name, vendor, path, url, cookie, date from history order by "); + tmp.append("date DESC limit "); + tmp.append(limitStr.str()); + ret = sqlite3_prepare_v2(historyDb, tmp.c_str(), -1, &stmt, NULL); + if (ret != SQLITE_OK) + FINALIZE_ON_ERROR(stmt); + + for (;;) { + ret = sqlite3_step(stmt); + if (ret == SQLITE_ROW) { + const char *tempStr = NULL; + string arg = string(); + string url = string(); + string cookie = string(); + Item *item = Item::createHistoryItem(); + if (!item) { + DP_LOGE("Fail to create item"); + break; + } + item->setHistoryId(sqlite3_column_int(stmt,0)); + item->setDownloadType((DL_TYPE::TYPE)sqlite3_column_int(stmt,1)); + item->setContentType(sqlite3_column_int(stmt,2)); + item->setState((ITEM::STATE)sqlite3_column_int(stmt,3)); + item->setErrorCode((ERROR::CODE)sqlite3_column_int(stmt,4)); + tempStr = (const char *)(sqlite3_column_text(stmt,5)); + if (tempStr) { + arg = tempStr; + if (item->downloadType() == DL_TYPE::MIDP_DOWNLOAD) + item->setContentName(arg); + item->setTitle(arg); + } + tempStr = (const char *)(sqlite3_column_text(stmt,6)); + if (tempStr) + arg = tempStr; + item->setVendorName(arg); + tempStr = (const char *)(sqlite3_column_text(stmt,7)); + if (tempStr) + arg = tempStr; + item->setRegisteredFilePath(arg); + tempStr = (const char *)(sqlite3_column_text(stmt,8)); + if (tempStr) + url = tempStr; + tempStr = (const char *)(sqlite3_column_text(stmt,9)); + if (tempStr) + cookie = tempStr; + item->setFinishedTime(sqlite3_column_double(stmt,10)); + item->attachHistoryItem(); + item->setRetryData(url, cookie); + } else + break; + } + DP_LOGD("SQL error: %d", ret); + + if (sqlite3_finalize(stmt) != SQLITE_OK) + DP_LOGE("sqlite3_finalize is failed."); + close(); + + if (ret == SQLITE_DONE || ret == SQLITE_ROW) + return true; + else + return false; +} + +bool DownloadHistoryDB::deleteItem(unsigned int historyId) +{ + int ret = 0; + sqlite3_stmt *stmt = NULL; + + DP_LOG_FUNC(); + + if (!open()) { + DP_LOGE("historyDB is NULL"); + return false; + } + + ret = sqlite3_prepare_v2(historyDb, "delete from history where historyid=?", + -1, &stmt, NULL); + + if (ret != SQLITE_OK) + FINALIZE_ON_ERROR(stmt); + if (sqlite3_bind_int(stmt, 1, historyId) != SQLITE_OK) + DP_LOGE("sqlite3_bind_int is failed."); + ret = sqlite3_step(stmt); + if (ret != SQLITE_OK && ret != SQLITE_DONE) + FINALIZE_ON_ERROR(stmt); + + if (sqlite3_finalize(stmt) != SQLITE_OK) + DP_LOGE("sqlite3_finalize is failed."); + close(); + return true; +} + +bool DownloadHistoryDB::deleteMultipleItem(queue &q) +{ + int ret = 0; + unsigned int historyId = -1; + sqlite3_stmt *stmt = NULL; + char *errmsg = NULL; + + DP_LOG_FUNC(); + + if (!open()) { + DP_LOGE("historyDB is NULL"); + return false; + } + ret = sqlite3_exec(historyDb, "PRAGMA synchronous=OFF;\ + PRAGMA count_changes=OFF; PRAGMA temp_store=memory;", + NULL, NULL, &errmsg); + if (SQLITE_OK != ret) { + sqlite3_free(errmsg); + close(); + return false; + } + + DP_LOGD("queue size[%d]",q.size()); + while (!q.empty()) { + ret = sqlite3_prepare_v2(historyDb, "delete from history where historyid=?", + -1, &stmt, NULL); + if (ret != SQLITE_OK) + FINALIZE_ON_ERROR(stmt); + historyId = q.front(); + q.pop(); + if (sqlite3_bind_int(stmt, 1, historyId) != SQLITE_OK) + DP_LOGE("sqlite3_bind_int is failed."); + ret = sqlite3_step(stmt); + if (ret != SQLITE_OK && ret != SQLITE_DONE) + FINALIZE_ON_ERROR(stmt); + } + + if (sqlite3_finalize(stmt) != SQLITE_OK) + DP_LOGE("sqlite3_finalize is failed."); + close(); + return true; +} + +bool DownloadHistoryDB::clearData(void) +{ + int ret = 0; + sqlite3_stmt *stmt = NULL; + + DP_LOG_FUNC(); + + if (!open()) { + DP_LOGE("historyDB is NULL"); + return false; + } + + ret = sqlite3_prepare_v2(historyDb, "delete from history", -1, &stmt, NULL); + if (ret != SQLITE_OK) + FINALIZE_ON_ERROR(stmt); + + ret = sqlite3_step(stmt); + if (ret != SQLITE_DONE) + FINALIZE_ON_ERROR(stmt); + + if (sqlite3_finalize(stmt) != SQLITE_OK) + DP_LOGE("sqlite3_finalize is failed."); + close(); + return true; +} + diff --git a/src/download-provider-item.cpp b/src/download-provider-item.cpp new file mode 100644 index 0000000..df3d892 --- /dev/null +++ b/src/download-provider-item.cpp @@ -0,0 +1,653 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-item.cpp + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief item class for saving download data + */ +// FIXME later : move to util clas +#include "download-provider-item.h" +#include "download-provider-common.h" +#include "download-provider-items.h" +#include "download-provider-viewItem.h" +#include "download-provider-history-db.h" +#include "download-provider-network.h" +#include +#include + +Item::Item() + : m_state(ITEM::IDLE) + , m_errorCode(ERROR::NONE) + , m_historyId(-1) + , m_contentType(DP_CONTENT_UNKOWN) + , m_finishedTime(0) + , m_downloadType(DL_TYPE::TYPE_NONE) + , m_gotFirstData(false) +{ +// FIXME Later : init private members +} + +Item::Item(DownloadRequest &rRequest) + : m_state(ITEM::IDLE) + , m_errorCode(ERROR::NONE) + , m_historyId(-1) + , m_contentType(DP_CONTENT_UNKOWN) + , m_finishedTime(0) + , m_downloadType(DL_TYPE::TYPE_NONE) + , m_gotFirstData(false) +{ + m_title = S_("IDS_COM_BODY_NO_NAME"); + m_iconPath = DP_UNKNOWN_ICON_PATH; + m_aptr_request = auto_ptr(new DownloadRequest(rRequest)); // FIXME ??? +} + +Item::~Item() +{ + DP_LOGD_FUNC(); +} + +void Item::create(DownloadRequest &rRequest) +{ +// DP_LOGD_FUNC(); + + Item *newItem = new Item(rRequest); + + Items &items = Items::getInstance(); + items.attachItem(newItem); + + ViewItem::create(newItem); + DP_LOGD("newItem[%p]",newItem); + + newItem->download(); +} + +Item *Item::createHistoryItem() +{ + string url = string(); + string cookie = string(); + DownloadRequest request(url,cookie); + Item *newItem = new Item(request); +// DP_LOGD_FUNC(); + + DP_LOGD("new History Item[%p]",newItem); + + return newItem; +} + +void Item::attachHistoryItem() +{ + Items &items = Items::getInstance(); + + DP_LOGD("attach History Item[%p]",this); + items.attachItem(this); + ViewItem::create(this); + extractIconPath(); +} + +void Item::destroy() +{ +// DP_LOG_FUNC(); + // FIXME prohibit to destroy if downloading + if (!isFinished()) { + DP_LOGE("Cannot delete this item. State[%d]",m_state); + return; + } + DP_LOGD("Item::destroy() notify()"); + + setState(ITEM::DESTROY); + notify(); +// DP_LOG("Item::destroy() notify()... END"); + m_aptr_downloadItem->deSubscribe(m_aptr_downloadObserver.get()); + if (m_aptr_downloadObserver.get()) + m_aptr_downloadObserver->clear(); + else + DP_LOGE("download observer pointer is NULL"); + /* When deleting item after download is failed */ + if (m_aptr_netEventObserver.get()) { + NetMgr &netMgrInstance = NetMgr::getInstance(); + netMgrInstance.deSubscribe(m_aptr_netEventObserver.get()); + } + Items::getInstance().detachItem(this); +} + +void Item::deleteFromDB() +{ + DownloadHistoryDB::deleteItem(m_historyId); +} + +void Item::download() +{ + NetMgr &netMgrInstance = NetMgr::getInstance(); + +// DP_LOGD_FUNC(); + + setState(ITEM::REQUESTING); + + createSubscribeData(); + + netMgrInstance.subscribe(m_aptr_netEventObserver.get()); + + m_aptr_downloadItem->start(); + + DP_LOG("Item::download() notify()"); + notify(); +} + +void Item::createSubscribeData() // autoptr's variable of this class. +{ + m_aptr_downloadObserver = auto_ptr( + new Observer(updateCBForDownloadObserver, this, "downloadItemObserver")); + m_aptr_netEventObserver = auto_ptr( + new Observer(netEventCBObserver, this, "netMgrObserver")); + m_aptr_downloadItem = auto_ptr(new DownloadItem(m_aptr_request)); + if (!m_aptr_downloadItem.get()) { + DP_LOGE("Fail to create download item"); + return; + } + m_aptr_downloadItem->subscribe(m_aptr_downloadObserver.get()); +} + +void Item::startUpdate(void) +{ + if (m_gotFirstData) { + setState(ITEM::DOWNLOADING); + if (!registeredFilePath().empty()) + /* need to parse title again, because installed path can be changed */ + extractTitle(); + return; + } + + DP_LOGD_FUNC(); + + if (!m_aptr_downloadItem.get()) { + DP_LOGE("Fail to get download item"); + return; + } + m_gotFirstData = true; +// setState(ITEM::DOWNLOADING); + setState(ITEM::RECEIVING_DOWNLOAD_INFO); + + extractTitle(); + DownloadUtil &util = DownloadUtil::getInstance(); + m_contentType = util.getContentType( + m_aptr_downloadItem->mimeType().c_str(), filePath().c_str()); + extractIconPath(); +} + +void Item::updateFromDownloadItem(void) +{ +// DP_LOGD_FUNC(); + + switch (m_aptr_downloadItem->state()) { + case DL_ITEM::STARTED: + break; + case DL_ITEM::UPDATING: + startUpdate(); + break; + case DL_ITEM::COMPLETE_DOWNLOAD: + setState(ITEM::REGISTERING_TO_SYSTEM); + /* need to parse title again, because installed path can be changed */ + //extractTitle(); + break; + case DL_ITEM::INSTALL_NOTIFY: + setState(ITEM::NOTIFYING_TO_SERVER); + break; + case DL_ITEM::START_DRM_DOMAIN: + setState(ITEM::PROCESSING_DOMAIN); + break; + case DL_ITEM::FINISH_DRM_DOMAIN: + setState(ITEM::FINISH_PROCESSING_DOMAIN); + break; + case DL_ITEM::WAITING_RO: + setState(ITEM::ACTIVATING); + break; + case DL_ITEM::SUSPENDED: + setState(ITEM::SUSPEND); + m_aptr_downloadItem->resume(); + break; + case DL_ITEM::RESUMED: + //setState(ITEM::RESUMED); + break; + case DL_ITEM::FINISHED: + setState(ITEM::FINISH_DOWNLOAD); + handleFinishedItem(); + break; + case DL_ITEM::CANCELED: + /* Already update for cancel state in case of cancellation from user Response popup */ + if (state() == ITEM::CANCEL) { + DP_LOGD("Already cancelled when closing OMA download popup"); + return; + } else { + setState(ITEM::CANCEL); + handleFinishedItem(); + } + break; + case DL_ITEM::FAILED: + setState(ITEM::FAIL_TO_DOWNLOAD); + setErrorCode(m_aptr_downloadItem->errorCode()); + handleFinishedItem(); + break; + case DL_ITEM::WAITING_CONFIRM: + setState(ITEM::WAITING_USER_RESPONSE); + break; + default: + break; + } + + DP_LOGD("Item[%p]::updateFromDownloadItem() notify() dl_state[%d]state[%d]", this, m_aptr_downloadItem->state(), state()); + notify(); +} +void Item::handleFinishedItem() +{ + createHistoryId(); + m_finishedTime = time(NULL); + DownloadHistoryDB::addToHistoryDB(this); + /* If download is finished, it is not need to get network event */ + if (m_aptr_netEventObserver.get()) { + NetMgr &netMgrInstance = NetMgr::getInstance(); + netMgrInstance.deSubscribe(m_aptr_netEventObserver.get()); + } +} + +const char *Item::getErrorMessage(void) +{ + switch (m_errorCode) { + case ERROR::NETWORK_FAIL: + return S_("IDS_COM_POP_CONNECTION_FAILED"); + + case ERROR::INVALID_URL: + return S_("IDS_COM_POP_INVALID_URL"); + + case ERROR::NOT_ENOUGH_MEMORY: + return S_("IDS_COM_POP_NOT_ENOUGH_MEMORY"); + + case ERROR::FAIL_TO_INSTALL: + return __("IDS_BR_POP_INSTALLATION_FAILED"); + + case ERROR::OMA_POPUP_TIME_OUT: + return S_("IDS_COM_POP_CANCELLED") ; + + case ERROR::FAIL_TO_PARSE_DESCRIPTOR: + return __("IDS_BR_POP_INVALIDDESCRIPTOR") ; + + case ERROR::UNKNOWN: + case ERROR::ENGINE_FAIL: + return S_("IDS_COM_POP_FAILED") ; + default: + return NULL; + } +} + +void Item::extractTitle(void) +{ + if (!m_aptr_downloadItem.get()) { + DP_LOGE("Fail to get download item"); + return; + } + DP_LOGD("title [%s] filePath [%s]", m_title.c_str(), filePath().c_str()); + if ((m_aptr_downloadItem->downloadType() == DL_TYPE::OMA_DOWNLOAD || + m_aptr_downloadItem->downloadType() == DL_TYPE::MIDP_DOWNLOAD) && + !m_aptr_downloadItem->contentName().empty()) { + m_title = m_aptr_downloadItem->contentName(); + } else { + size_t found = 0; + string path; + if (!registeredFilePath().empty()) + path = registeredFilePath(); + else + path = filePath(); + found = path.find_last_of("/"); + if (found != string::npos) + m_title = path.substr(found+1); + } +} + +void Item::extractIconPath() +{ + // FIXME Later : change 2 dimension array?? + switch(m_contentType) { + case DP_CONTENT_IMAGE : + m_iconPath = DP_IMAGE_ICON_PATH; + break; + case DP_CONTENT_VIDEO : + m_iconPath = DP_VIDEO_ICON_PATH; + break; + case DP_CONTENT_MUSIC: + m_iconPath = DP_MUSIC_ICON_PATH; + break; + case DP_CONTENT_PDF: + m_iconPath = DP_PDF_ICON_PATH; + break; + case DP_CONTENT_WORD: + m_iconPath = DP_WORD_ICON_PATH; + break; + case DP_CONTENT_PPT: + m_iconPath = DP_PPT_ICON_PATH; + break; + case DP_CONTENT_EXCEL: + m_iconPath = DP_EXCEL_ICON_PATH; + break; + case DP_CONTENT_HTML: + m_iconPath = DP_HTML_ICON_PATH; + break; + case DP_CONTENT_TEXT: + m_iconPath = DP_TEXT_ICON_PATH; + break; + case DP_CONTENT_RINGTONE: + m_iconPath = DP_RINGTONE_ICON_PATH; + break; + case DP_CONTENT_DRM: + m_iconPath = DP_DRM_ICON_PATH; + break; + case DP_CONTENT_JAVA: + m_iconPath = DP_JAVA_ICON_PATH; + break; + case DP_CONTENT_UNKOWN: + default: + m_iconPath = DP_UNKNOWN_ICON_PATH; + } +} + +void Item::updateCBForDownloadObserver(void *data) +{ + DP_LOGD_FUNC(); + if (data) + static_cast(data)->updateFromDownloadItem(); +} + +void Item::netEventCBObserver(void *data) +{ + /* It is only considerd that there is one network event which is suspend now. + * If other network evnet is added, + * it is needed to add function accroding to what kinds of network event is + **/ + DP_LOG_FUNC(); + if (data) + static_cast(data)->suspend(); +} + +void Item::sendUserResponse(bool res) +{ + bool ret = false; + DP_LOG_FUNC(); + if (!m_aptr_downloadItem.get()) { + DP_LOGE("Fail to get download item"); + return; + } + ret = m_aptr_downloadItem->sendUserResponse(res); + if (ret) { + /* Update UI at once if the user cancel the oma download + * But this is really needed?? + */ + if (!res) { + setState(ITEM::CANCEL); + handleFinishedItem(); + notify(); + } else { + setState(ITEM::RECEIVING_DOWNLOAD_INFO); + } + } +} + +bool Item::play() +{ + if (m_contentType == DP_CONTENT_JAVA && + m_aptr_downloadItem->downloadType() == DL_TYPE::MIDP_DOWNLOAD) { + string pkgName; + DownloadUtil &util = DownloadUtil::getInstance(); + pkgName = util.getMidletPkgName(m_contentName, m_vendorName); + return m_fileOpener.openApp(pkgName); + } else { + return m_fileOpener.openFile(registeredFilePath(), m_contentType); + } +} + +/* Test code */ +const char *Item::stateStr(void) +{ + switch((int)state()) { + case ITEM::IDLE: + return "IDLE"; + case ITEM::REQUESTING: + return "REQUESTING"; + case ITEM::PREPARE_TO_RETRY: + return "PREPARE_TO_RETRY"; + case ITEM::WAITING_USER_RESPONSE: + return "WAITING_USER_RESPONSE"; + case ITEM::RECEIVING_DOWNLOAD_INFO: + return "RECEIVING_DOWNLOAD_INFO"; + case ITEM::DOWNLOADING: + return "DOWNLOADING"; + case ITEM::REGISTERING_TO_SYSTEM: + return "REGISTERING_TO_SYSTEM"; + case ITEM::PROCESSING_DOMAIN: + return "PROCESSING_DOMAIN"; + case ITEM::FINISH_PROCESSING_DOMAIN: + return "FINISH_PROCESSING_DOMAIN"; + case ITEM::ACTIVATING: + return "ACTIVATING"; + case ITEM::NOTIFYING_TO_SERVER: + return "NOTIFYING_TO_SERVER"; + case ITEM::SUSPEND: + return "SUSPEND"; + case ITEM::FINISH_DOWNLOAD: + return "FINISH_DOWNLOAD"; + case ITEM::FAIL_TO_DOWNLOAD: + return "FAIL_TO_DOWNLOAD"; + case ITEM::CANCEL: + return "CANCEL"; + case ITEM::PLAY: + return "PLAY"; + case ITEM::DESTROY: + return "DESTROY"; + } + return "Unknown State"; +} + +DL_TYPE::TYPE Item::downloadType() +{ + if (m_downloadType == DL_TYPE::TYPE_NONE) { + if (!m_aptr_downloadItem.get()) { + DP_LOGE("Fail to get download item"); + return DL_TYPE::TYPE_NONE; + } + m_downloadType = m_aptr_downloadItem->downloadType(); + } + return m_downloadType; +} + +string &Item::contentName() +{ + if (m_contentName.empty()) { + if (!m_aptr_downloadItem.get()) { + DP_LOGE("Fail to get download item"); + return m_emptyString; + } + m_contentName = m_aptr_downloadItem->contentName(); + } + return m_contentName; +} + +string &Item::vendorName() +{ + if (m_vendorName.empty()) { + if (!m_aptr_downloadItem.get()) { + DP_LOGE("Fail to get download item"); + return m_emptyString; + } + m_vendorName = m_aptr_downloadItem->vendorName(); + } + return m_vendorName; +} + +string &Item::registeredFilePath() +{ + if (m_registeredFilePath.empty()) { + if (!m_aptr_downloadItem.get()) { + DP_LOGE("Fail to get download item"); + return m_emptyString; + } + m_registeredFilePath = m_aptr_downloadItem->registeredFilePath(); + } + return m_registeredFilePath; +} + +string &Item::url() +{ + if (m_url.empty()) { + if (!m_aptr_downloadItem.get()) { + DP_LOGE("Fail to get download item"); + return m_emptyString; + } + m_url = m_aptr_downloadItem->url(); + } + return m_url; +} + +string &Item::cookie() +{ + if (m_cookie.empty()) { + if (!m_aptr_downloadItem.get()) { + DP_LOGE("Fail to get download item"); + return m_emptyString; + } + m_cookie = m_aptr_downloadItem->cookie(); + } + return m_cookie; +} + + +void Item::createHistoryId() +{ + int count = 0; + unsigned tempId = time(NULL); + while (isExistedHistoryId(tempId)) { + srand((unsigned)(time(NULL))); + tempId = rand(); + count++; + if (count > 100) { + DP_LOGE("Fail to create unique ID"); + tempId = -1; + break; + } + DP_LOGD("random historyId[%ld]", m_historyId); + } + m_historyId = tempId; +} + +bool Item::isExistedHistoryId(unsigned int id) +{ + Items &items = Items::getInstance(); + return items.isExistedHistoryId(id); +} + +void Item::setRetryData(string &url, string &cookie) +{ + + m_url = url; + m_cookie = cookie; + m_aptr_request->setUrl(url); + m_aptr_request->setCookie(cookie); + + createSubscribeData(); + +} + +bool Item::retry() +{ + DP_LOG_FUNC(); + if (m_aptr_downloadItem.get()) { + NetMgr &netMgrInstance = NetMgr::getInstance(); + setState(ITEM::PREPARE_TO_RETRY); + notify(); + DownloadHistoryDB::deleteItem(m_historyId); + netMgrInstance.subscribe(m_aptr_netEventObserver.get()); + m_historyId = -1; + m_aptr_downloadItem->retry(); + return true; + } else { + m_state = ITEM::FAIL_TO_DOWNLOAD; + return false; + } +} + +void Item::clearForRetry() +{ + m_state = ITEM::IDLE; + m_errorCode = ERROR::NONE; + m_contentType = DP_CONTENT_UNKOWN; + m_finishedTime = 0; + m_downloadType = DL_TYPE::TYPE_NONE; + m_gotFirstData = false; +} + +bool Item::isFinished() +{ + bool ret = false; + switch (m_state) { + case ITEM::FINISH_DOWNLOAD: + case ITEM::FAIL_TO_DOWNLOAD: + case ITEM::CANCEL: + case ITEM::PLAY: + case ITEM::DESTROY: + ret = true; + break; + default: + ret = false; + } + return ret; +} + +bool Item::isFinishedWithErr() +{ + bool ret = false; + switch (m_state) { + case ITEM::FAIL_TO_DOWNLOAD: + case ITEM::CANCEL: + ret = true; + break; + default: + ret = false; + } + return ret; +} + +bool Item::isPreparingDownload() +{ + bool ret = false; + switch (m_state) { + case ITEM::IDLE: + case ITEM::REQUESTING: + case ITEM::PREPARE_TO_RETRY: + case ITEM::WAITING_USER_RESPONSE: + ret = true; + break; + default: + ret = false; + } + return ret; + +} + +bool Item::isCompletedDownload() +{ + if (isPreparingDownload() || m_state == ITEM::DOWNLOADING) + return false; + else + return true; +} + diff --git a/src/download-provider-items.cpp b/src/download-provider-items.cpp new file mode 100644 index 0000000..7fe1141 --- /dev/null +++ b/src/download-provider-items.cpp @@ -0,0 +1,52 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-items.cpp + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Interface API with item list + */ +#include "download-provider-items.h" + +void Items::attachItem(Item *item) +{ + m_items.push_back(item); +} + +void Items::detachItem(Item *item) +{ + vector::iterator it; + for (it = m_items.begin() ; it < m_items.end() ; it++) { + if (*it == item) { + m_items.erase(it); + delete item; + } + } +} + +bool Items::isExistedHistoryId(unsigned int id) +{ + vector ::iterator it; + for (it = m_items.begin(); it < m_items.end(); it++) { + if ((*it)->historyId() == id ) { + DP_LOGD("historyId[%ld],title[%s]", + (*it)->historyId(), (*it)->title().c_str()); + return true; + } + } + return false; +} + diff --git a/src/download-provider-network.cpp b/src/download-provider-network.cpp new file mode 100644 index 0000000..6c6fa90 --- /dev/null +++ b/src/download-provider-network.cpp @@ -0,0 +1,247 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-network.cpp + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Download netowkr manager + */ + +#include +#include "download-provider-common.h" +#include "download-provider-network.h" + +enum { + NET_INACTIVE = 0, + NET_WIFI_ACTIVE, + NET_CELLULAR_ACTIVE +}; + +NetMgr::NetMgr() +{ + m_netStatus = getConnectionState(); + if (m_netStatus == NET_WIFI_ACTIVE || + m_netStatus == NET_CELLULAR_ACTIVE) { + getProxy(); + getIPAddress(); + } +} + +NetMgr::~NetMgr() +{ +} + +void NetMgr::initNetwork() +{ + if (vconf_notify_key_changed(VCONFKEY_NETWORK_STATUS, + netStatusChangedCB, NULL) < 0) + DP_LOGE("Fail to register network status callback"); + if (vconf_notify_key_changed(VCONFKEY_NETWORK_CONFIGURATION_CHANGE_IND, + netConfigChangedCB, NULL) < 0) + DP_LOGE("Fail to register network config change callback"); +} + +void NetMgr::deinitNetwork() +{ + if (vconf_ignore_key_changed(VCONFKEY_NETWORK_STATUS, + netStatusChangedCB) < 0) + DP_LOGE("Fail to ignore network status callback"); + if (vconf_ignore_key_changed(VCONFKEY_NETWORK_CONFIGURATION_CHANGE_IND, + netConfigChangedCB) < 0) + DP_LOGE("Fail to ignore network config change callback"); +} + +int NetMgr::getConnectionState() +{ + int status = VCONFKEY_NETWORK_OFF; + int ret = 0; + + ret = vconf_get_int(VCONFKEY_NETWORK_STATUS, &status); + if (ret < 0) { + DP_LOGE(" Fail to get network status : err[%d]",ret); + return NET_INACTIVE; + } + switch (status) { + case VCONFKEY_NETWORK_OFF: + DP_LOG("VCONFKEY_NETWORK_OFF"); + ret = NET_INACTIVE; + break; + case VCONFKEY_NETWORK_CELLULAR: + DP_LOG("VCONFKEY_NETWORK_CELLULAR"); + ret = getCellularStatus(); + break; + case VCONFKEY_NETWORK_WIFI: + DP_LOG("VCONFKEY_NETWORK_WIFI"); + ret = getWifiStatus(); + break; + default: + DP_LOGE("Cannot enter here"); + ret = NET_INACTIVE; + } + return ret; +} + +int NetMgr::getCellularStatus() +{ + int status = VCONFKEY_NETWORK_CELLULAR_NO_SERVICE; + int ret = 0; + + ret = vconf_get_int(VCONFKEY_NETWORK_CELLULAR_STATE, &status); + + if (ret < 0) { + DP_LOGE(" Fail to get cellular status : err[%d]",ret); + return NET_INACTIVE; + } + + switch(status) { + case VCONFKEY_NETWORK_CELLULAR_ON: + DP_LOG("VCONFKEY_NETWORK_CELLULAR_ON"); + ret = NET_CELLULAR_ACTIVE; + break; + case VCONFKEY_NETWORK_CELLULAR_3G_OPTION_OFF: + DP_LOG("VCONFKEY_NETWORK_CELLULAR_3G_OPTION_OFF"); + ret = NET_INACTIVE; + break; + case VCONFKEY_NETWORK_CELLULAR_ROAMING_OFF: + DP_LOG("VCONFKEY_NETWORK_CELLULAR_ROAMING_OFF"); + ret = NET_INACTIVE; + break; + case VCONFKEY_NETWORK_CELLULAR_FLIGHT_MODE: + DP_LOG("VCONFKEY_NETWORK_CELLULAR_FLIGHT_MODE"); + ret = NET_INACTIVE; + break; + case VCONFKEY_NETWORK_CELLULAR_NO_SERVICE: + DP_LOG("VCONFKEY_NETWORK_CELLULAR_NO_SERVICE"); + ret = NET_INACTIVE; + break; + default: + DP_LOGE("Cannot enter here"); + ret = NET_INACTIVE; + } + return ret; + +} + +int NetMgr::getWifiStatus() +{ + int status = VCONFKEY_NETWORK_WIFI_OFF; + int ret = 0; + + ret = vconf_get_int(VCONFKEY_NETWORK_WIFI_STATE, &status); + + if (ret < 0) { + DP_LOGE(" Fail to get wifi status : err[%d]",ret); + return NET_INACTIVE; + } + + switch(status) { + case VCONFKEY_NETWORK_WIFI_CONNECTED: + DP_LOG("VCONFKEY_NETWORK_WIFI_CONNECTED"); + ret = NET_WIFI_ACTIVE; + break; + case VCONFKEY_NETWORK_WIFI_NOT_CONNECTED: + DP_LOG("VCONFKEY_NETWORK_WIFI_NOT_CONNECTED"); + ret = NET_INACTIVE; + break; + case VCONFKEY_NETWORK_WIFI_OFF: + DP_LOG("VCONFKEY_NETWORK_WIFI_OFF"); + ret = NET_INACTIVE; + break; + default: + DP_LOGE("Cannot enter here"); + ret = NET_INACTIVE; + } + return ret; +} + +void NetMgr::netStatusChanged() +{ + int changedStatus = NET_INACTIVE; + changedStatus = getConnectionState(); + DP_LOG("Previous[%d] Changed[%d]", m_netStatus, changedStatus); + if (m_netStatus != changedStatus) { + if (changedStatus == NET_INACTIVE) + DP_LOG("Netowrk is disconnected"); + else + DP_LOG("Network is connected"); + m_netStatus = changedStatus; + } else { + DP_LOGE("Network status is not changed. Cannot enter here"); + } +} + +void NetMgr::netConfigChanged() +{ + int status = 0; + int ret = 0; + + DP_LOG_FUNC(); + + ret = vconf_get_int(VCONFKEY_NETWORK_CONFIGURATION_CHANGE_IND, &status); + if (ret < 0) { + DP_LOGE("Fail to get network configuration change ind : err[%d]",ret); + return; + } + DP_LOG("netConfigChanged:status[%d]", status); + + + if (status) { /* true */ + getProxy(); + getIPAddress(); + /* This notify is only for suspend event. + * If othere network event is added, it is needed to save event types + * and get function for it + **/ + notify(); + } else { + DP_LOGE("Network connection is disconnected"); + } +} + +void NetMgr::getProxy() +{ + char *proxy = NULL; + proxy = vconf_get_str(VCONFKEY_NETWORK_PROXY); + if (proxy) { + DP_LOG("===== Proxy address[%s] =====", proxy); + free(proxy); + proxy = NULL; + } +} + +void NetMgr::getIPAddress() +{ + char *ipAddr = NULL; + ipAddr = vconf_get_str(VCONFKEY_NETWORK_IP); + if (ipAddr) { + DP_LOG("===== IP address[%s] =====", ipAddr); + free(ipAddr); + ipAddr= NULL; + } +} + +void NetMgr::netStatusChangedCB(keynode_t *keynode, void *data) +{ + NetMgr inst = NetMgr::getInstance(); + inst.netStatusChanged(); +} + +void NetMgr::netConfigChangedCB(keynode_t *keynode, void *data) +{ + NetMgr inst = NetMgr::getInstance(); + inst.netConfigChanged(); +} + diff --git a/src/download-provider-util.cpp b/src/download-provider-util.cpp new file mode 100644 index 0000000..cc4ba40 --- /dev/null +++ b/src/download-provider-util.cpp @@ -0,0 +1,283 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/* + * @file download-provider-util.cpp + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Utility APIs and interface with content player + */ + +#include +#include +#include +#include "aul.h" +#include "xdgmime.h" +#include "app_service.h" + +#include "download-provider-util.h" + +#define JAVA_ENG_PATH "/usr/lib/libjava-installer.so" + +struct MimeTableType +{ + const char *mime; + int contentType; +}; + +#define MAX_MIME_TABLE_NUM 22 +const char *ambiguousMIMETypeList[] = { + "text/plain", + "application/octet-stream" +}; + +struct MimeTableType MimeTable[]={ + // PDF + {"application/pdf",DP_CONTENT_PDF}, + // word + {"application/msword",DP_CONTENT_WORD}, + {"application/vnd.openxmlformats-officedocument.wordprocessingml.document",DP_CONTENT_WORD}, + // ppt + {"application/vnd.ms-powerpoint",DP_CONTENT_PPT}, + {"application/vnd.openxmlformats-officedocument.presentationml.presentation",DP_CONTENT_PPT}, + // excel + {"application/vnd.ms-excel",DP_CONTENT_EXCEL}, + {"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",DP_CONTENT_EXCEL}, + // html + {"text/html",DP_CONTENT_HTML}, + // txt + {"text/txt",DP_CONTENT_TEXT}, + {"text/palin",DP_CONTENT_TEXT}, + // ringtone + {"text/x-iMelody",DP_CONTENT_RINGTONE},//10 + {"application/x-smaf",DP_CONTENT_RINGTONE}, + {"audio/midi",DP_CONTENT_RINGTONE}, + {"audio/AMR",DP_CONTENT_RINGTONE}, + {"audio/AMR-WB",DP_CONTENT_RINGTONE}, + {"audio/x-xmf",DP_CONTENT_RINGTONE}, + // DRM + {"application/vnd.oma.drm.content",DP_CONTENT_DRM}, + {"application/vnd.oma.drm.message",DP_CONTENT_DRM}, + // JAVA + {"application/x-java-archive",DP_CONTENT_JAVA}, + {"application/java-archive",DP_CONTENT_JAVA}, + // SVG + {"image/svg+xml",DP_CONTENT_SVG}, //20 + // FLASH + {"application/x-shockwave-flash",DP_CONTENT_FLASH} +}; + +bool FileOpener::openFile(string &path, int contentType) +{ + service_h handle = NULL; + string filePath; + DP_LOG_FUNC(); + + if (path.empty()) + return false; + + DP_LOG("path [%s]", path.c_str()); + if (service_create(&handle) < 0) { + DP_LOGE("Fail to create service handle"); + return false; + } + + if (!handle) { + DP_LOGE("service handle is null"); + return false; + } + + if (service_set_operation(handle, SERVICE_OPERATION_VIEW) < 0) { + DP_LOGE("Fail to set service operation"); + service_destroy(handle); + return false; + } + + if (contentType == DP_CONTENT_HTML) { + filePath = "file://"; + filePath.append(path.c_str()); + } else { + filePath = path; + } + if (service_set_uri(handle, filePath.c_str()) < 0) { + DP_LOGE("Fail to set uri"); + service_destroy(handle); + return false; + } + + if (service_send_launch_request(handle, NULL, NULL) < 0) { + DP_LOGE("Fail to launch service"); + service_destroy(handle); + return false; + } + + service_destroy(handle); + + return true; +} + +bool FileOpener::openApp(string &pkgName) +{ + service_h handle = NULL; + DP_LOG_FUNC(); + if (pkgName.empty()) + return false; + + if (service_create(&handle) < 0) { + DP_LOGE("Fail to create service handle"); + return false; + } + + if (!handle) { + DP_LOGE("service handle is null"); + return false; + } + + if (service_set_package(handle, pkgName.c_str()) < 0) { + DP_LOGE("Fail to set service operation"); + service_destroy(handle); + return false; + } + + if (service_send_launch_request(handle, NULL, NULL) < 0) { + DP_LOGE("Fail to aul open"); + service_destroy(handle); + return false; + } + + service_destroy(handle); + + return true; +} + + +DownloadUtil::DownloadUtil() +{ + initDrm(); +} + +string DownloadUtil::getMidletPkgName(string& name, string& vendor) +{ + string pkgName = string(); + char appName[MAX_FILE_PATH_LEN] = {0,}; + void *handle = NULL; + int (*java_get_pkgname )(char *,char *,char *) = NULL; + + if (name.length() < 1 || vendor.length() < 1) + return pkgName; + + handle = dlopen(JAVA_ENG_PATH, RTLD_LAZY); + if ( handle == NULL ) { + DP_LOGE("dlopen error\n"); + if(handle) + dlclose(handle); + return pkgName; + } + + java_get_pkgname = (int(*)(char *,char *,char *)) dlsym( handle, "jim_get_suite_pkgname_with_vendor_suite_name"); + if ( java_get_pkgname == NULL ) { + DP_LOGE("dlopen error2\n"); + dlclose(handle); + return pkgName; + } + DP_LOG("vendor name[%s] midlet name[%s]",vendor.c_str(),name.c_str()); + + if (java_get_pkgname((char *)vendor.c_str(), (char *)name.c_str(), appName)) { + DP_LOG("pkg name[%s]\n",appName); + pkgName = appName; + } + dlclose(handle); + return pkgName; +} + +void DownloadUtil::initDrm() +{ + DP_LOG_FUNC(); +} + +int DownloadUtil::getContentType(const char *mime, const char *filePath) +{ + int i = 0; + int type = DP_CONTENT_UNKOWN; + int ret = 0; + char tempMime[MAX_FILE_PATH_LEN] = {0,}; + DP_LOGD_FUNC(); + if (mime == NULL || strlen(mime) < 1) + return DP_CONTENT_UNKOWN; + + DP_LOG("mime[%s]",mime); + strncpy(tempMime, mime, MAX_FILE_PATH_LEN-1); + if (isAmbiguousMIMEType(mime)) { + if (filePath) { + memset(tempMime, 0x00, MAX_FILE_PATH_LEN); + ret = aul_get_mime_from_file(filePath,tempMime,sizeof(tempMime)); + if (ret < AUL_R_OK ) + strncpy(tempMime, mime, MAX_FILE_PATH_LEN-1); + else + DP_LOG("mime from extension name[%s]",tempMime); + } + } + + /* Search a content type from mime table. */ + for (i = 0; i < MAX_MIME_TABLE_NUM; i++) + { + //DP_LOG("TableMime[%d][%s]",i,MimeTable[i].mime); + if (strncmp(MimeTable[i].mime, tempMime, strlen(tempMime)) == 0){ + type = MimeTable[i].contentType; + break; + } + } + /* If there is no mime at mime table, check the category with the first + * domain of mime string + * ex) video/... => video type */ + if (type == DP_CONTENT_UNKOWN) + { + const char *unaliasedMime = NULL; + /* unaliased_mimetype means representative mime among similar types */ + unaliasedMime = xdg_mime_unalias_mime_type(tempMime); + + if (unaliasedMime != NULL) { + DP_LOG("unaliased mime type[%s]\n",unaliasedMime); + if (strstr(unaliasedMime,"video/") != NULL) + type = DP_CONTENT_VIDEO; + else if (strstr(unaliasedMime,"audio/") != NULL) + type = DP_CONTENT_MUSIC; + else if (strstr(unaliasedMime,"image/") != NULL) + type = DP_CONTENT_IMAGE; + } + } + DP_LOG("type[%d]\n",type); + return type; +} + +bool DownloadUtil::isAmbiguousMIMEType(const char *mimeType) +{ + + if (!mimeType) + return false; + + int index = 0; + int listSize = sizeof(ambiguousMIMETypeList) / sizeof(const char *); + for (index = 0; index < listSize; index++) { + if (0 == strncmp(mimeType, ambiguousMIMETypeList[index], + strlen(ambiguousMIMETypeList[index]))) { + DP_LOG("It is ambiguous! [%s]", ambiguousMIMETypeList[index]); + return true; + } + } + + return false; +} + diff --git a/src/download-provider-view.cpp b/src/download-provider-view.cpp new file mode 100644 index 0000000..102d034 --- /dev/null +++ b/src/download-provider-view.cpp @@ -0,0 +1,1174 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-view.cpp + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief UI manager class for download list view and delete view + */ +#include +#include +#include "download-provider-view.h" +#include "download-provider-history-db.h" +#include "download-provider-downloadItem.h" + +static void destroy_window_cb(void *data, Evas_Object *obj, void *event); + +enum { + DOWNLOAD_NOTIFY_SELECTED, + DOWNLOAD_NOTIFY_DELETED +}; + +DownloadView::DownloadView(void) + : eoWindow(NULL) + , eoBackground(NULL) + , eoLayout(NULL) + , eoNaviBar(NULL) + , eoNaviBarItem(NULL) + , eoBackBtn(NULL) + , eoControlBar(NULL) + , eoCbItemDelete(NULL) + , eoCbItemCancel(NULL) + , eoCbItemEmpty(NULL) + , eoBoxLayout(NULL) + , eoBox(NULL) + , eoDldList(NULL) + , eoPopup(NULL) + , eoSelectAllLayout(NULL) + , eoAllCheckedBox(NULL) + , eoNotifyInfo(NULL) + , eoNotifyInfoLayout(NULL) + , m_allChecked(EINA_FALSE) + , m_viewItemCount(0) +{ +// FIXME Later : init private members + DownloadEngine &engine = DownloadEngine::getInstance(); + engine.initEngine(); + DateUtil &inst = DateUtil::getInstance(); + inst.updateLocale(); + dldGenlistGroupStyle.item_style = "grouptitle"; + dldGenlistGroupStyle.func.text_get = getGenlistGroupLabelCB; + dldGenlistGroupStyle.func.content_get = NULL; + dldGenlistGroupStyle.func.state_get = NULL; + dldGenlistGroupStyle.func.del = NULL; + + m_today.setType(DATETIME::DATE_TYPE_TODAY); + m_yesterday.setType(DATETIME::DATE_TYPE_YESTERDAY); + m_previousDay.setType(DATETIME::DATE_TYPE_PREVIOUS); +} + +DownloadView::~DownloadView() +{ + DP_LOG_FUNC(); + DownloadEngine &engine = DownloadEngine::getInstance(); + engine.deinitEngine(); +} + +Evas_Object *DownloadView::create(void) +{ + Evas_Object *window = NULL; + window = createWindow(PACKAGE); + if (!window) + return NULL; + + createBackground(window); + createLayout(window); + setIndicator(window); + createView(); + + return window; +} + +void DownloadView::show() +{ + DP_LOG_FUNC(); + elm_win_raise(eoWindow); + handleUpdateDateGroupType(NULL); +} + +void DownloadView::hide() +{ + DP_LOG_FUNC(); + removePopup(); + destroyNotifyInfo(); + if (isGenlistEditMode()) { + hideGenlistEditMode(); + } + elm_win_lower(eoWindow); +} + +void DownloadView::activateWindow() +{ + if (!eoWindow) + create(); + + show(); +} + +void DownloadView::showViewItem(int id, const char *title) +{ + DP_LOG_FUNC(); +} + +/* This is called by AUL view mode */ +void DownloadView::playContent(int id, const char *title) +{ + DP_LOG_FUNC(); +} + +void DownloadView::setIndicator(Evas_Object *window) +{ + elm_win_indicator_mode_set(window, ELM_WIN_INDICATOR_SHOW); +} + +Evas_Object *DownloadView::createWindow(const char *windowName) +{ + eoWindow = elm_win_add(NULL, windowName, ELM_WIN_BASIC); + if (eoWindow) { + elm_win_title_set(eoWindow, __("IDS_BR_HEADER_DOWNLOAD_MANAGER")); + elm_win_borderless_set(eoWindow, EINA_TRUE); + elm_win_conformant_set(eoWindow, 1); + evas_object_smart_callback_add(eoWindow, "delete,request", + destroy_window_cb, static_cast(this)); + } + return eoWindow; +} + +Evas_Object *DownloadView::createBackground(Evas_Object *window) +{ + if (!window) + return NULL; + + eoBackground = elm_bg_add(window); + if (eoBackground) { + evas_object_size_hint_weight_set(eoBackground, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(window, eoBackground); + evas_object_show(eoBackground); + } else { + DP_LOGE("Fail to create bg object"); + } + return eoBackground; +} + +Evas_Object *DownloadView::createLayout(Evas_Object *parent) +{ + if (!parent) { + DP_LOGE("Invalid Paramter"); + return NULL; + } + + eoLayout = elm_layout_add(parent); + if (eoLayout) { + if (!elm_layout_theme_set(eoLayout, "layout", "application", "default" )) + DP_LOGE("Fail to set elm_layout_theme_set"); + + evas_object_size_hint_weight_set(eoLayout, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_win_resize_object_add(parent, eoLayout); + + edje_object_signal_emit(elm_layout_edje_get(eoLayout), "elm,state,show,indicator", "elm"); + evas_object_show(eoLayout); + } else { + DP_LOGE("Fail to create layout"); + } + return eoLayout; +} + +void DownloadView::createView() +{ + DP_LOG_FUNC(); + createNaviBar(); + createList(); + if (m_viewItemCount < 1) + showEmptyView(); +} + +void DownloadView::createNaviBar() +{ + DP_LOGD_FUNC(); + eoNaviBar = elm_naviframe_add(eoLayout); + elm_object_part_content_set(eoLayout, "elm.swallow.content", eoNaviBar); + createBackBtn(); + createBox(); + eoNaviBarItem = elm_naviframe_item_push(eoNaviBar, + __("IDS_BR_HEADER_DOWNLOAD_MANAGER"),eoBackBtn, NULL, eoBoxLayout, NULL); + createControlBar(); + evas_object_show(eoNaviBar); + +} + +void DownloadView::createBackBtn() +{ + DP_LOGD_FUNC(); + eoBackBtn = elm_button_add(eoNaviBar); + elm_object_style_set(eoBackBtn, "naviframe/end_btn/default"); + evas_object_smart_callback_add(eoBackBtn, "clicked", backBtnCB,NULL); + evas_object_show(eoBackBtn); +} + +void DownloadView::createControlBar() +{ + DP_LOGD_FUNC(); + + eoControlBar = elm_toolbar_add(eoNaviBar); + if (eoControlBar == NULL) + return; + elm_toolbar_shrink_mode_set(eoControlBar, ELM_TOOLBAR_SHRINK_EXPAND); + eoCbItemDelete = elm_toolbar_item_append(eoControlBar, NULL, + S_("IDS_COM_OPT_DELETE"), cbItemDeleteCB, eoNaviBar); + eoCbItemEmpty = elm_toolbar_item_append(eoControlBar, NULL, NULL, NULL, NULL); + elm_object_item_part_content_set(eoNaviBarItem, "controlbar", + eoControlBar); + elm_object_item_disabled_set(eoCbItemDelete, EINA_TRUE); + elm_object_item_disabled_set(eoCbItemEmpty, EINA_TRUE); + evas_object_show(eoControlBar); +} + +void DownloadView::createBox() +{ + DP_LOGD_FUNC(); + eoBoxLayout = elm_layout_add(eoNaviBar); + elm_layout_theme_set(eoBoxLayout, "layout", "application", "noindicator"); + evas_object_size_hint_weight_set(eoBoxLayout, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + eoBox = elm_box_add(eoBoxLayout); + elm_object_part_content_set(eoBoxLayout, "elm.swallow.content", eoBox ); + + evas_object_show(eoBox); + evas_object_show(eoBoxLayout); +} + +void DownloadView::createList() +{ + //DP_LOGD_FUNC(); + eoDldList = elm_genlist_add(eoBoxLayout); + DP_LOGD("create::eoDldList[%p]",eoDldList); +/* When using ELM_LIST_LIMIT, the window size is broken at the landscape mode */ + evas_object_size_hint_weight_set(eoDldList, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(eoDldList, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_genlist_homogeneous_set(eoDldList, EINA_TRUE); + elm_genlist_block_count_set(eoDldList,8); + + elm_box_pack_end(eoBox, eoDldList); + evas_object_show(eoDldList); +} + +void destroy_window_cb(void *data, Evas_Object *obj, void *event) +{ + DP_LOG_FUNC(); + elm_exit(); +} + +void DownloadView::changedRegion() +{ + DateUtil &inst = DateUtil::getInstance(); + inst.updateLocale(); + elm_genlist_realized_items_update(eoDldList); +} + +void DownloadView::attachViewItem(ViewItem *viewItem) +{ + DP_LOG_FUNC(); + if (m_viewItemCount < 1) { + hideEmptyView(); + createList(); + } + if (viewItem) { + addViewItemToGenlist(viewItem); + m_viewItemCount++; + } +} + +void DownloadView::detachViewItem(ViewItem *viewItem) +{ + DP_LOG("delete viewItem[%p]",viewItem); + if (viewItem) { + delete viewItem; + m_viewItemCount--; + } + if (!isGenlistEditMode() && + (m_viewItemCount < 1)) + showEmptyView(); +} + +void DownloadView::update() +{ + Elm_Object_Item *it = NULL; + DP_LOG_FUNC(); + if (!eoDldList) { + DP_LOGE("download list is NULL"); + return; + } + it = elm_genlist_first_item_get(eoDldList); + while (it) { + DP_LOGD("glItem[%p]",it); + elm_genlist_item_update(it); + it = elm_genlist_item_next_get(it); + } +} + +void DownloadView::update(ViewItem *viewItem) +{ + if (!viewItem) + return; + + DP_LOG("DownloadView::update viewItem [%p]", viewItem); + elm_genlist_item_update(viewItem->genlistItem()); +} + +void DownloadView::update(Elm_Object_Item *glItem) +{ + if (!glItem) + return; + + DP_LOG("DownloadView::update glItem [%p]", glItem); + elm_genlist_item_update(glItem); +} + +void DownloadView::addViewItemToGenlist(ViewItem *viewItem) +{ + DP_LOG_FUNC(); + handleUpdateDateGroupType(viewItem); + createGenlistItem(viewItem); +} + +void DownloadView::createGenlistItem(ViewItem *viewItem) +{ + Elm_Object_Item *glItem = NULL; + Elm_Object_Item *glGroupItem = NULL; + /* EAPI Elm_Object_Item *elm_genlist_item_prepend( + * Evas_Object *obj, + * const Elm_Genlist_Item_Class *itc, + * const void *data, + * Elm_Object_Item *parent, + * Elm_Genlist_Item_Type flags, + * Evas_Smart_Cb func, + * const void *func_data) EINA_ARG_NONNULL(1); */ + glGroupItem = getGenlistGroupItem(viewItem->dateGroupType()); + DP_LOGD("group item[%p]",glGroupItem); + if (!glGroupItem) { + DateGroup *dateGrpObj = getDateGroupObj(viewItem->dateGroupType()); + if (!viewItem->isFinished()) { + glGroupItem = elm_genlist_item_prepend( + eoDldList, + &dldGenlistGroupStyle, + static_cast(dateGrpObj), + NULL, + ELM_GENLIST_ITEM_GROUP, + NULL, + NULL); + } else { + /* Download History Item */ + glGroupItem = elm_genlist_item_append( + eoDldList, + &dldGenlistGroupStyle, + static_cast(dateGrpObj), + NULL, + ELM_GENLIST_ITEM_GROUP, + NULL, + NULL); + } + if (!glGroupItem) + DP_LOGE("Fail to add a genlist group item"); + else + elm_genlist_item_select_mode_set(glGroupItem, + ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY); + setGenlistGroupItem(viewItem->dateGroupType(), glGroupItem); + } + increaseGenlistGroupCount(viewItem->dateGroupType()); + if (!viewItem->isFinished()) { + glItem = elm_genlist_item_insert_after( + eoDldList, + viewItem->elmGenlistStyle(), + static_cast(viewItem), + glGroupItem, + glGroupItem, + ELM_GENLIST_ITEM_NONE, + genlistClickCB, + static_cast(viewItem)); + } else { + /* Download History Item */ + glItem = elm_genlist_item_append( + eoDldList, + viewItem->elmGenlistStyle(), + static_cast(viewItem), + glGroupItem, + ELM_GENLIST_ITEM_NONE, + genlistClickCB, + static_cast(viewItem)); + } + if (!glItem) + DP_LOGE("Fail to add a genlist item"); + + DP_LOGD("genlist groupItem[%p] item[%p] viewItem[%p]", glGroupItem, glItem, viewItem); + viewItem->setGenlistItem(glItem); + /* Move scrollbar to top. + * When groupItem means today group in case of addtion of download link item + **/ + if (!viewItem->isFinished()) + elm_genlist_item_show(glGroupItem, ELM_GENLIST_ITEM_SCROLLTO_TOP); + +} + +void DownloadView::showEmptyView() +{ + DP_LOGD_FUNC(); + if (!eoEmptyNoContent) { + eoEmptyNoContent = elm_layout_add(eoLayout); + elm_layout_theme_set(eoEmptyNoContent, "layout", "nocontents", "text"); + evas_object_size_hint_weight_set(eoEmptyNoContent, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(eoEmptyNoContent, EVAS_HINT_FILL, EVAS_HINT_FILL); + elm_object_part_text_set(eoEmptyNoContent, "elm.text", + __("IDS_DL_BODY_NO_DOWNLOADS")); + evas_object_size_hint_weight_set (eoEmptyNoContent, + EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + + if (eoDldList) { + elm_box_unpack(eoBox,eoDldList); + /* Detection code */ + DP_LOGD("del::eoDldList[%p]",eoDldList); + evas_object_del(eoDldList); + eoDldList = NULL; + } + elm_box_pack_start(eoBox, eoEmptyNoContent); + } + evas_object_show(eoEmptyNoContent); + elm_object_item_disabled_set(eoCbItemDelete, EINA_TRUE); +} + +void DownloadView::hideEmptyView() +{ + DP_LOGD_FUNC(); + if(eoEmptyNoContent) { + elm_box_unpack(eoBox, eoEmptyNoContent); + evas_object_del(eoEmptyNoContent); + eoEmptyNoContent = NULL; + } + elm_object_item_disabled_set(eoCbItemDelete, EINA_FALSE); +} + +bool DownloadView::isGenlistEditMode() +{ + return (bool)elm_genlist_decorate_mode_get(eoDldList); +} + +void DownloadView::createSelectAllLayout() +{ + eoSelectAllLayout = elm_layout_add(eoBox); + elm_layout_theme_set(eoSelectAllLayout, "genlist", "item", + "select_all/default"); + evas_object_size_hint_weight_set(eoSelectAllLayout, EVAS_HINT_EXPAND, + EVAS_HINT_FILL); + evas_object_size_hint_align_set(eoSelectAllLayout, EVAS_HINT_FILL, + EVAS_HINT_FILL); + evas_object_event_callback_add(eoSelectAllLayout, EVAS_CALLBACK_MOUSE_DOWN, + selectAllClickedCB, NULL); + eoAllCheckedBox = elm_check_add(eoSelectAllLayout); + elm_check_state_pointer_set(eoAllCheckedBox, &m_allChecked); + evas_object_smart_callback_add(eoAllCheckedBox, "changed", + selectAllChangedCB, NULL); + evas_object_propagate_events_set(eoAllCheckedBox, EINA_FALSE); + elm_object_part_content_set(eoSelectAllLayout, "elm.icon", eoAllCheckedBox); + elm_object_text_set(eoSelectAllLayout, S_("IDS_COM_BODY_SELECT_ALL")); + elm_box_pack_start(eoBox, eoSelectAllLayout); + evas_object_show(eoSelectAllLayout); + m_allChecked = EINA_FALSE; +} + +void DownloadView::changeAllCheckedValue() +{ + m_allChecked = !m_allChecked; + elm_check_state_pointer_set(eoAllCheckedBox, &m_allChecked); + handleChangedAllCheckedState(); +} + +void DownloadView::destroyCheckedItem() +{ + Eina_List *list = NULL; + Elm_Object_Item *it = NULL; + ViewItem *item = NULL; + int checkedCount = 0; + queue deleteQueue; + + DP_LOGD_FUNC(); + + it = elm_genlist_first_item_get(eoDldList); + + while (it) { + item = (ViewItem *)elm_object_item_data_get(it); + /* elm_genlist_item_select_mode_get is needed to check group item */ + if (elm_genlist_item_select_mode_get(it) != + ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY && + item && item->checkedValue()) { + list = eina_list_append(list, it); + } + it = elm_genlist_item_next_get(it); + } + + if (!list) { + DP_LOGD("There is no delete item"); + return; + } + + checkedCount = eina_list_count(list); + if (checkedCount < 1) + return; + DP_LOGD("checkedCount[%d]", checkedCount); + + for (int i = 0; i < checkedCount; i++) + { + it = (Elm_Object_Item *)eina_list_data_get(list); + if (it) + item = (ViewItem *)elm_object_item_data_get(it); + else + DP_LOGE("genlist item is null"); + list = eina_list_next(list); + if (item) { + deleteQueue.push(item->historyId()); + item->destroy(); + } else { + DP_LOGE("viewItem is null"); + } + } + if (list) + eina_list_free(list); + + DownloadHistoryDB::deleteMultipleItem(deleteQueue); + showNotifyInfo(DOWNLOAD_NOTIFY_DELETED, checkedCount); + hideGenlistEditMode(); +} + +void DownloadView::showGenlistEditMode() +{ + DP_LOG_FUNC(); + /* Initialize notify info widget */ + destroyNotifyInfo(); + elm_object_item_text_set(eoNaviBarItem, S_("IDS_COM_OPT_DELETE")); + /* Change layoutbackground color to edit mode color */ + elm_object_style_set(eoBackground, "edit_mode"); + /* Disable the back button of control bar */ + elm_object_item_part_content_unset(eoNaviBarItem, "prev_btn"); + destroyEvasObj(eoBackBtn); + + if (eoCbItemEmpty) + elm_object_item_del(eoCbItemEmpty); + eoCbItemCancel = elm_toolbar_item_append(eoControlBar, NULL, + S_("IDS_COM_SK_CANCEL"), cbItemCancelCB, eoNaviBar); + + /* Append 'Select All' layout */ + createSelectAllLayout(); + /* Set reorder end edit mode */ + elm_genlist_reorder_mode_set(eoDldList, EINA_TRUE); + elm_genlist_decorate_mode_set(eoDldList, EINA_TRUE); + /* This means even if the ouside of checked box is selected, + it is same to click a check box. */ + elm_genlist_select_mode_set(eoDldList, ELM_OBJECT_SELECT_MODE_ALWAYS); + + Elm_Object_Item *it = NULL; + ViewItem *viewItem = NULL; + it = elm_genlist_first_item_get(eoDldList); + while (it) { + viewItem = (ViewItem *)elm_object_item_data_get(it); + if (elm_genlist_item_select_mode_get(it) != + ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY && + viewItem && !(viewItem->isFinished())) + elm_object_item_disabled_set(it, EINA_TRUE); + it = elm_genlist_item_next_get(it); + } + elm_object_item_disabled_set(eoCbItemDelete, EINA_TRUE); +} + +void DownloadView::hideGenlistEditMode() +{ + DP_LOG_FUNC(); + + elm_object_item_text_set(eoNaviBarItem, __("IDS_BR_HEADER_DOWNLOAD_MANAGER")); + elm_object_style_set(eoBackground, "default"); + + /* Recreate back button */ + createBackBtn(); + elm_object_item_part_content_set(eoNaviBarItem, "prev_btn", eoBackBtn); + + if (eoCbItemCancel) { + elm_object_item_del(eoCbItemCancel); + eoCbItemCancel = NULL; + } + eoCbItemEmpty = elm_toolbar_item_append(eoControlBar, NULL, NULL, NULL, NULL); + elm_object_item_disabled_set(eoCbItemEmpty, EINA_TRUE); + + elm_box_unpack(eoBox, eoSelectAllLayout); + + destroyEvasObj(eoAllCheckedBox); + destroyEvasObj(eoSelectAllLayout); + + elm_genlist_reorder_mode_set(eoDldList, EINA_FALSE); + elm_genlist_decorate_mode_set(eoDldList, EINA_FALSE); + elm_genlist_select_mode_set(eoDldList, ELM_OBJECT_SELECT_MODE_DEFAULT); + + Elm_Object_Item *it = NULL; + ViewItem *viewItem = NULL; + it = elm_genlist_first_item_get(eoDldList); + while (it) { + viewItem = (ViewItem *)elm_object_item_data_get(it); + if (elm_genlist_item_select_mode_get(it) != + ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY && viewItem) { + if (elm_object_item_disabled_get(it)) + elm_object_item_disabled_set(it, EINA_FALSE); + viewItem->setCheckedValue(EINA_FALSE); + viewItem->setCheckedBtn(NULL); + } + it = elm_genlist_item_next_get(it); + } + + m_allChecked = EINA_FALSE; + + if (m_viewItemCount < 1) { + elm_object_item_disabled_set(eoCbItemDelete, EINA_TRUE); + showEmptyView(); + } else + elm_object_item_disabled_set(eoCbItemDelete, EINA_FALSE); +} + +void DownloadView::handleChangedAllCheckedState() +{ + int checkedCount = 0; + Elm_Object_Item *it = NULL; + ViewItem *viewItem = NULL; + it = elm_genlist_first_item_get(eoDldList); + while (it) { + viewItem = (ViewItem *)elm_object_item_data_get(it); + if (elm_genlist_item_select_mode_get(it) != + ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY && viewItem) { + if (viewItem->isFinished()) { + viewItem->setCheckedValue(m_allChecked); + viewItem->updateCheckedBtn(); + checkedCount++; + } + } + it = elm_genlist_item_next_get(it); + } + + if (m_allChecked && checkedCount > 0) { + elm_object_item_disabled_set(eoCbItemDelete, EINA_FALSE); + showNotifyInfo(DOWNLOAD_NOTIFY_SELECTED, checkedCount); + } else { + elm_object_item_disabled_set(eoCbItemDelete, EINA_TRUE); + showNotifyInfo(DOWNLOAD_NOTIFY_SELECTED, 0); + } +} + +void DownloadView::handleCheckedState() +{ + int checkedCount = 0; + int deleteAbleTotalCount = 0; + + DP_LOGD_FUNC(); + + Elm_Object_Item *it = NULL; + ViewItem *viewItem = NULL; + it = elm_genlist_first_item_get(eoDldList); + while (it) { + viewItem = (ViewItem *)elm_object_item_data_get(it); + if (elm_genlist_item_select_mode_get(it) != + ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY && viewItem) { + if (viewItem->checkedValue()) + checkedCount++; + if (viewItem->isFinished()) + deleteAbleTotalCount++; + } + it = elm_genlist_item_next_get(it); + } + + if (checkedCount == deleteAbleTotalCount) + m_allChecked = EINA_TRUE; + else + m_allChecked = EINA_FALSE; + elm_check_state_pointer_set(eoAllCheckedBox, &m_allChecked); + + if (checkedCount == 0) { + elm_object_item_disabled_set(eoCbItemDelete, EINA_TRUE); + destroyNotifyInfo(); + } else + elm_object_item_disabled_set(eoCbItemDelete, EINA_FALSE); + showNotifyInfo(DOWNLOAD_NOTIFY_SELECTED, checkedCount); +} +void DownloadView::createNotifyInfo() +{ + DP_LOGD_FUNC(); + eoNotifyInfo = elm_notify_add(eoBoxLayout); + elm_notify_orient_set(eoNotifyInfo, ELM_NOTIFY_ORIENT_BOTTOM); + evas_object_size_hint_weight_set(eoNotifyInfo, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(eoNotifyInfo, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_event_callback_add(eoNotifyInfo, EVAS_CALLBACK_SHOW, showNotifyInfoCB, eoLayout); + evas_object_event_callback_add(eoNotifyInfo, EVAS_CALLBACK_HIDE, hideNotifyInfoCB, eoLayout); + eoNotifyInfoLayout = elm_layout_add(eoNotifyInfo); + elm_object_content_set(eoNotifyInfo, eoNotifyInfoLayout); +} + +void DownloadView::showNotifyInfo(int type, int selectedCount) +{ + string buf; + DP_LOGD_FUNC(); + + if (selectedCount == 0) { + destroyNotifyInfo(); + return; + } + + if (!eoNotifyInfo) + createNotifyInfo(); + + elm_layout_theme_set(eoNotifyInfoLayout, "standard", "selectioninfo", + "vertical/bottom_12"); + buf.append(" "); + if (type == DOWNLOAD_NOTIFY_SELECTED) { + stringstream countStr; + countStr << selectedCount; + buf = S_("IDS_COM_BODY_SELECTED"); + buf.append(" ("); + buf.append(countStr.str()); + buf.append(")"); + } else if (type == DOWNLOAD_NOTIFY_DELETED) { + buf = S_("IDS_COM_POP_DELETED"); + elm_notify_timeout_set(eoNotifyInfo, 3); + } + edje_object_part_text_set(_EDJ(eoNotifyInfoLayout), "elm.text", buf.c_str()); + evas_object_show(eoNotifyInfo); +} + +void DownloadView::destroyNotifyInfo() +{ + DP_LOGD_FUNC(); + destroyEvasObj(eoNotifyInfoLayout); + destroyEvasObj(eoNotifyInfo); + eoNotifyInfoLayout = NULL; + eoNotifyInfo = NULL; +} + +/* Static callback function */ +void DownloadView::showNotifyInfoCB(void *data, Evas *evas, Evas_Object *obj, + void *event) +{ + Evas_Object *layout = (Evas_Object *)data; + if (!data) { + DP_LOGE("data is NULL"); + return; + } + edje_object_signal_emit(_EDJ(layout), "elm,layout,content,bottom_padding", + "layout"); +} + +void DownloadView::hideNotifyInfoCB(void *data, Evas *evas, Evas_Object *obj, + void *event) +{ + Evas_Object *layout = (Evas_Object *)data; + if (!data) { + DP_LOGE("data is NULL"); + return; + } + edje_object_signal_emit(_EDJ(layout), "elm,layout,content,default", "layout"); +} + +void DownloadView::selectAllClickedCB(void *data, Evas *evas, Evas_Object *obj, + void *event_info) +{ + DownloadView &view = DownloadView::getInstance(); + DP_LOGD_FUNC(); + view.changeAllCheckedValue(); +} + +void DownloadView::selectAllChangedCB(void *data, Evas_Object *obj, + void *event_info) +{ + DownloadView &view = DownloadView::getInstance(); + DP_LOGD_FUNC(); + view.handleChangedAllCheckedState(); +} + +void DownloadView::backBtnCB(void *data, Evas_Object *obj, void *event_info) +{ + DownloadView& view = DownloadView::getInstance(); + view.hide(); +} + +void DownloadView::cbItemDeleteCB(void *data, Evas_Object *obj, void *event_info) +{ + + DownloadView& view = DownloadView::getInstance(); + if (!view.isGenlistEditMode()) + view.showGenlistEditMode(); + else + view.destroyCheckedItem(); +} + +void DownloadView::cbItemCancelCB(void *data, Evas_Object *obj, void *event_info) +{ + DownloadView& view = DownloadView::getInstance(); + view.destroyNotifyInfo(); + view.hideGenlistEditMode(); +} + +void DownloadView::genlistClickCB(void *data, Evas_Object *obj, void *event_info) +{ + ViewItem *item = reinterpret_cast(data); + DP_LOGD_FUNC(); + if (!data) { + DP_LOGE("data is NULL"); + return; + } + item->clickedGenlistItem(); +} + +void DownloadView::cancelClickCB(void *data, Evas_Object *obj, void *event_info) +{ + ViewItem *item = NULL; + + DP_LOGD_FUNC(); + + if (!data) { + DP_LOGE("data is NULL"); + return; + } + item = reinterpret_cast(data); + item->requestCancel(); + +} + +void DownloadView::showErrPopup(string &desc) +{ + removePopup(); + + eoPopup = elm_popup_add(eoWindow); + evas_object_size_hint_weight_set(eoPopup, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_object_text_set(eoPopup, desc.c_str()); + elm_popup_timeout_set(eoPopup, 2); + evas_object_smart_callback_add(eoPopup, "response", errPopupResponseCB, NULL); + evas_object_show(eoPopup); +} + +void DownloadView::showOMAPopup(string &msg, ViewItem *viewItem) +{ + Evas_Object *btn1 = NULL; + Evas_Object *btn2 = NULL; + DP_LOGD_FUNC(); + /* If another popup is shown, delete it*/ + removePopup(); + eoPopup = elm_popup_add(eoWindow); + evas_object_size_hint_weight_set(eoPopup, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_object_text_set(eoPopup, msg.c_str()); + elm_object_part_text_set(eoPopup, "title,text", __("IDS_BR_POP_DOWNLOAD_Q")); + btn1 = elm_button_add(eoPopup); + elm_object_text_set(btn1, S_("IDS_COM_SK_OK")); + elm_object_part_content_set(eoPopup, "button1", btn1); + evas_object_smart_callback_add(btn1, "clicked", omaPopupResponseOKCB, + viewItem); + btn2 = elm_button_add(eoPopup); + elm_object_text_set(btn2, S_("IDS_COM_POP_CANCEL")); + elm_object_part_content_set(eoPopup, "button2", btn2); + evas_object_smart_callback_add(btn2, "clicked", omaPopupResponseCancelCB, + viewItem); + evas_object_show(eoPopup); +} + +void DownloadView::errPopupResponseCB(void *data, Evas_Object *obj, void *event_info) +{ + DP_LOGD_FUNC(); + DownloadView& view = DownloadView::getInstance(); + view.removePopup(); +} + +void DownloadView::omaPopupResponseOKCB(void *data, Evas_Object *obj, + void *event_info) +{ + ViewItem *viewItem = (ViewItem *)data; + DownloadView& view = DownloadView::getInstance(); + + DP_LOGD_FUNC(); + if (viewItem) + viewItem->sendUserResponse(true); + else + DP_LOGE("No viewItem"); + view.removePopup(); +} + +void DownloadView::omaPopupResponseCancelCB(void *data, Evas_Object *obj, + void *event_info) +{ + ViewItem *viewItem = (ViewItem *)data; + DownloadView& view = DownloadView::getInstance(); + + DP_LOGD_FUNC(); + if (viewItem) + viewItem->sendUserResponse(false); + else + DP_LOGE("No viewItem"); + view.removePopup(); +} + +void DownloadView::removePopup() +{ + DP_LOGD_FUNC(); + destroyEvasObj(eoPopup); +} + +DateGroup *DownloadView::getDateGroupObj(int type) +{ + DateGroup *obj = NULL; + switch (type) { + case DATETIME::DATE_TYPE_LATER: + case DATETIME::DATE_TYPE_TODAY: + obj = &m_today; + break; + case DATETIME::DATE_TYPE_YESTERDAY: + obj = &m_yesterday; + break; + case DATETIME::DATE_TYPE_PREVIOUS: + obj = &m_previousDay; + break; + default: + obj = NULL; + DP_LOGE("Cannot enter here"); + } + return obj; +} + +Elm_Object_Item *DownloadView::getGenlistGroupItem(int type) +{ + DateGroup *obj = getDateGroupObj(type); + if (!obj) + return NULL; + return obj->glGroupItem(); +} + +void DownloadView::setGenlistGroupItem(int type, Elm_Object_Item *item) +{ + DateGroup *obj = getDateGroupObj(type); + if (!obj) + return; + obj->setGlGroupItem(item); +} + +void DownloadView::increaseGenlistGroupCount(int type) +{ + DateGroup *obj = getDateGroupObj(type); + if (!obj) + return; + if (type == DATETIME::DATE_TYPE_TODAY || type == DATETIME::DATE_TYPE_LATER) { + if (m_today.getCount() < 1) { + DateUtil &inst = DateUtil::getInstance(); + inst.setTodayStandardTime(); + } + } + obj->increaseCount(); + DP_LOGD("increased count[%d]",obj->getCount()); +} + +int DownloadView::getGenlistGroupCount(int type) +{ + DateGroup *obj = getDateGroupObj(type); + if (!obj) + return 0; + DP_LOGD("Group count[%d]",obj->getCount()); + return obj->getCount(); +} + +void DownloadView::handleGenlistGroupItem(int type) +{ + DateGroup *obj = getDateGroupObj(type); + if (!obj) + return; + obj->decreaseCount(); + DP_LOGD("count[%d]type[%d]",obj->getCount(),type); + if (obj->getCount() < 1) { + //DP_LOGD("Group Item[%p][%d]", obj->glGroupItem(),type); + elm_object_item_del(obj->glGroupItem()); + obj->setGlGroupItem(NULL); + } +} + +void DownloadView::handleUpdateDateGroupType(ViewItem *viewItem) +{ + int diffDays = 0; + DateUtil &inst = DateUtil::getInstance(); + DP_LOGD_FUNC(); + diffDays = inst.getDiffDaysFromToday(); + if (viewItem) { + /* Update a view item which is added now + * This should be only called when attaching item + **/ + viewItem->extractDateGroupType(); + } else if (diffDays != 0) { + /* FIXME later + * Now, it is recreated download items and group items. + * Consider to move only group item later. + * This should be only called from show() function + **/ +/* FIXME later + * Another problem is happend becuase eina list is used repacing with vector */ +#if 0 + cleanGenlistData(); + Elm_Object_Item *it = NULL; + ViewItem *viewItem = NULL; + it = elm_genlist_first_item_get(eoDldList); + while (it) { + viewItem = (ViewItem *)elm_object_item_data_get(it); + if (!viewItem || elm_genlist_item_select_mode_get(it) != + ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY) + continue; + viewItem->extractDateGroupType(); + createGenlistItem(viewItem); + it = elm_genlist_item_next_get(it); + } +#endif + } + inst.setTodayStandardTime(); +} + +void DownloadView::moveRetryItem(ViewItem *viewItem) +{ + Elm_Object_Item *todayGroupItem = NULL; + Elm_Object_Item *firstItem = NULL; + DP_LOGD_FUNC(); + if (!viewItem) { + DP_LOGE("view item is NULL"); + return; + } + firstItem = elm_genlist_first_item_get(eoDldList); + if (firstItem) { + DP_LOGD("groupItem[%p] viewItem[%p]", firstItem, viewItem); + /* This is group item */ + if (elm_genlist_item_select_mode_get(firstItem) == + ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY) { + /* The top item is the item after group item */ + firstItem = elm_genlist_item_next_get(firstItem); + DP_LOGD("firstItem[%p], present item[%p]", firstItem, viewItem->genlistItem()); + if (firstItem == viewItem->genlistItem()) { + DP_LOGD("This is already top item. Don't need to move"); + return; + } + } + } + elm_object_item_del(viewItem->genlistItem()); + viewItem->setGenlistItem(NULL); + handleGenlistGroupItem(viewItem->dateGroupType()); + todayGroupItem = getGenlistGroupItem(DATETIME::DATE_TYPE_TODAY); + if (!todayGroupItem) { + DateGroup *dateGrpObj = getDateGroupObj(DATETIME::DATE_TYPE_TODAY); + todayGroupItem = elm_genlist_item_prepend( + eoDldList, + &dldGenlistGroupStyle, + static_cast(dateGrpObj), + NULL, + ELM_GENLIST_ITEM_GROUP, + NULL, + NULL); + setGenlistGroupItem(DATETIME::DATE_TYPE_TODAY, todayGroupItem); + if (!todayGroupItem) + DP_LOGE("Fail to add a genlist group item"); + else + elm_genlist_item_select_mode_set(todayGroupItem, + ELM_OBJECT_SELECT_MODE_DISPLAY_ONLY); + } + increaseGenlistGroupCount(DATETIME::DATE_TYPE_TODAY); + Elm_Object_Item *glItem = elm_genlist_item_insert_after( + eoDldList, + viewItem->elmGenlistStyle(), + static_cast(viewItem), + todayGroupItem, + todayGroupItem, + ELM_GENLIST_ITEM_NONE, + genlistClickCB, + static_cast(viewItem)); + if (!glItem) + DP_LOGE("Fail to add a genlist item"); + DP_LOGD("genlist groupItem[%p] item[%p] viewItem[%p]", todayGroupItem, + glItem, viewItem); + viewItem->setGenlistItem(glItem); + elm_genlist_item_show(todayGroupItem, ELM_GENLIST_ITEM_SCROLLTO_TOP); + viewItem->extractDateGroupType(); +} + +char *DownloadView::getGenlistGroupLabel(void *data, Evas_Object *obj, const char *part) +{ + DateGroup *dateGrp = static_cast(data); + + if(!data || !obj || !part) + return NULL; + + DP_LOGD("ViewItem::getListGroupLabel:part[%s] groupDateType[%d] obj[%p]", part, dateGrp->getType(), obj); + if (strncmp(part, "elm.text", strlen("elm.text")) == 0) { + DateUtil &inst = DateUtil::getInstance(); + string msg; + string outBuf; + double udateTime = 0; + switch (dateGrp->getType()) { + case DATETIME::DATE_TYPE_PREVIOUS: + msg = S_("IDS_COM_BODY_PREVIOUS_DAYS"); + break; + case DATETIME::DATE_TYPE_YESTERDAY: + udateTime = inst.yesterdayTime()*1000; + msg = S_("IDS_COM_BODY_YESTERDAY"); + msg += " ("; + inst.getDateStr(LOCALE_STYLE::FULL_DATE, udateTime, outBuf); + msg += outBuf; + msg += ")"; + break; + case DATETIME::DATE_TYPE_LATER: + case DATETIME::DATE_TYPE_TODAY: + udateTime = inst.nowTime()*1000; + msg = S_("IDS_COM_BODY_TODAY"); + msg += " ("; + inst.getDateStr(LOCALE_STYLE::FULL_DATE, udateTime, outBuf); + msg += outBuf; + msg += ")"; + break; + default : + DP_LOGE("Cannot enter here"); + return NULL; + } + return strdup(msg.c_str()); + } + return NULL; +} + +char *DownloadView::getGenlistGroupLabelCB(void *data, Evas_Object *obj, const char *part) +{ +// DP_LOGD_FUNC(); + if(!data || !obj || !part) + return NULL; + + DownloadView &view = DownloadView::getInstance(); + return view.getGenlistGroupLabel(data, obj, part); +} + +void DownloadView::cleanGenlistData() +{ + Elm_Object_Item *grpItem = NULL; + DP_LOGD_FUNC(); + grpItem = m_today.glGroupItem(); + if (grpItem) + elm_object_item_del(grpItem); + m_today.initData(); + grpItem = m_yesterday.glGroupItem(); + if (grpItem) + elm_object_item_del(grpItem); + m_yesterday.initData(); + grpItem = m_previousDay.glGroupItem(); + if (grpItem) + elm_object_item_del(grpItem); + m_previousDay.initData(); + elm_genlist_clear(eoDldList); +} + diff --git a/src/download-provider-viewItem.cpp b/src/download-provider-viewItem.cpp new file mode 100644 index 0000000..2f4ca8a --- /dev/null +++ b/src/download-provider-viewItem.cpp @@ -0,0 +1,580 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-viewItem.cpp + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief item data class for download view + */ +#include "download-provider-viewItem.h" +#include "download-provider-items.h" +#include "download-provider-view.h" + +ViewItem::ViewItem(Item *item) + : m_item(item) + , m_glItem(NULL) + , m_progressBar(NULL) + , m_checkedBtn(NULL) + , m_checked(EINA_FALSE) + , m_isRetryCase(false) + , m_dateGroupType(DATETIME::DATE_TYPE_NONE) +{ + // FIXME need to makes exchange subject?? not yet, but keep it in mind! + if (item) { + m_aptr_observer = auto_ptr( + new Observer(updateCB, this, "viewItemObserver")); + item->subscribe(m_aptr_observer.get()); + } + + dldGenlistStyle.item_style = "3text.3icon"; + dldGenlistStyle.func.text_get = getGenlistLabelCB; + dldGenlistStyle.func.content_get = getGenlistIconCB; + dldGenlistStyle.func.state_get = NULL; + dldGenlistStyle.func.del = NULL; + dldGenlistStyle.decorate_all_item_style = "edit_default"; + + dldHistoryGenlistStyle.item_style = "3text.1icon.2"; + dldHistoryGenlistStyle.func.text_get = getGenlistLabelCB; + dldHistoryGenlistStyle.func.content_get = getGenlistIconCB; + dldHistoryGenlistStyle.func.state_get = NULL; + dldHistoryGenlistStyle.func.del = NULL; + dldHistoryGenlistStyle.decorate_all_item_style = "edit_default"; + + dldGenlistSlideStyle.item_style = "3text.1icon.2"; + dldGenlistSlideStyle.func.text_get = getGenlistLabelCB; + dldGenlistSlideStyle.func.content_get= getGenlistIconCB; + dldGenlistSlideStyle.func.state_get = NULL; + dldGenlistSlideStyle.func.del = NULL; + dldGenlistSlideStyle.decorate_all_item_style = "edit_default"; + +} + +ViewItem::~ViewItem() +{ + DP_LOGD_FUNC(); +} + +void ViewItem::create(Item *item) +{ + ViewItem *newViewItem = new ViewItem(item); + + DownloadView &view = DownloadView::getInstance(); + view.attachViewItem(newViewItem); +} + +void ViewItem::destroy() +{ + DP_LOGD("ViewItem::destroy"); + /* After item is destory, + view item also will be destroyed through event system */ + if (m_item) + m_item->destroy(); +} + +void ViewItem::updateCB(void *data) +{ + if (data) + static_cast(data)->updateFromItem(); +} + +void ViewItem::updateFromItem() +{ + DownloadView &view = DownloadView::getInstance(); + DP_LOGD("ViewItem::updateFromItem() ITEM::[%d]", state()); + if (state() == ITEM::DESTROY) { + int tempType = 0; + DP_LOGD("ViewItem::updateFromItem() ITEM::DESTROY"); + if (m_item) + m_item->deSubscribe(m_aptr_observer.get()); + m_aptr_observer->clear(); + elm_object_item_del(m_glItem); + m_glItem = NULL; + tempType = dateGroupType(); + view.detachViewItem(this); + view.handleGenlistGroupItem(tempType); + return; + } + + if (state() == ITEM::WAITING_USER_RESPONSE) { + string buf; + buf.append("Name : "); + buf.append(m_item->contentName()); + buf.append("
"); + buf.append("Size : "); + buf.append(getHumanFriendlyBytesStr(fileSize(), false)); + buf.append("
"); + buf.append("Vendor : "); + buf.append(m_item->vendorName()); + buf.append("
"); + if (m_item->isMidletInstalled()) { + buf.append("
"); + buf.append(S_("IDS_COM_POP_ALREDY_EXISTS")); + buf.append("
"); + buf.append("Want to update?"); + } + view.showOMAPopup(buf, this); + return; + } + + if (state() == ITEM::DOWNLOADING) { + if (fileSize() > 0 && m_progressBar) { + double percentageProgress = 0.0; + percentageProgress = (double)(receivedFileSize()) / + (double)(fileSize()); + DP_LOGD("progress value[%.2f]",percentageProgress); + elm_progressbar_value_set(m_progressBar, percentageProgress); + } + elm_genlist_item_fields_update(m_glItem,"elm.text.2", + ELM_GENLIST_ITEM_FIELD_TEXT); + } else if (m_isRetryCase && state() == ITEM::RECEIVING_DOWNLOAD_INFO) { + elm_genlist_item_item_class_update(m_glItem, &dldGenlistStyle); + } else if (!isFinished()) { + elm_genlist_item_update(m_glItem); + } else {/* finished state */ + if (state() == ITEM::FINISH_DOWNLOAD) + elm_genlist_item_item_class_update(m_glItem, &dldHistoryGenlistStyle); + else + elm_genlist_item_item_class_update(m_glItem, &dldGenlistSlideStyle); + if (view.isGenlistEditMode()) + elm_object_item_disabled_set(m_glItem, EINA_FALSE); + } +} + +char *ViewItem::getGenlistLabelCB(void *data, Evas_Object *obj, const char *part) +{ +// DP_LOGD_FUNC(); + + if(!data || !obj || !part) + return NULL; + + ViewItem *item = static_cast(data); + return item->getGenlistLabel(obj, part); +} + +char *ViewItem::getGenlistLabel(Evas_Object *obj, const char *part) +{ + DP_LOGD("ViewItem::getListLabel:part[%s]", part); + + if (strncmp(part, "elm.text.1", strlen("elm.text.1")) == 0) { + return strdup(getTitle()); + } else if (strncmp(part, "elm.text.2", strlen("elm.text.2")) == 0) { + return strdup(getMessage()); + } else if (strncmp(part, "elm.text.3", strlen("elm.text.3")) == 0) { + if (!isFinished()) { + return NULL; + } else { + string outBuf; + DateUtil &inst = DateUtil::getInstance(); + double udateTime = finishedTime() * 1000; + if (dateGroupType() == DATETIME::DATE_TYPE_PREVIOUS + || dateGroupType() == DATETIME::DATE_TYPE_LATER) + inst.getDateStr(LOCALE_STYLE::SHORT_DATE, udateTime, outBuf); + else + inst.getDateStr(LOCALE_STYLE::TIME, udateTime, outBuf); + return strdup(outBuf.c_str()); + } + } else { + DP_LOGD("No Implementation"); + return NULL; + } +} + +Evas_Object *ViewItem::getGenlistIconCB(void *data, Evas_Object *obj, + const char *part) +{ +// DP_LOGD_FUNC(); + if(!data || !obj || !part) { + DP_LOGE("parameter is NULL"); + return NULL; + } + + ViewItem *item = static_cast(data); + return item->getGenlistIcon(obj, part); +} + +Evas_Object *ViewItem::getGenlistIcon(Evas_Object *obj, const char *part) +{ + //DP_LOGD("ViewItem::getGenlistIcon:part[%s]state[%s]", part, stateStr()); + + if (elm_genlist_decorate_mode_get(obj) && isFinished()) { + if (strncmp(part,"elm.edit.icon.1", strlen("elm.edit.icon.1")) == 0) { + Evas_Object *checkBtn = elm_check_add(obj); + elm_check_state_pointer_set(checkBtn, &m_checked); + evas_object_smart_callback_add(checkBtn, "changed", checkChangedCB, + this); + m_checkedBtn = checkBtn; + return checkBtn; + } else if (strncmp(part,"elm.edit.icon.2", strlen("elm.edit.icon.2")) == + 0) { + return NULL; + } + + } + /* elm.icon.2 should be checked prior to elm.icon */ + if (strncmp(part,"elm.icon.2", strlen("elm.icon.2")) == 0) { + if (state() == ITEM::RECEIVING_DOWNLOAD_INFO || + state() == ITEM::PREPARE_TO_RETRY || + state() == ITEM::DOWNLOADING || + isPreparingDownload()) + return createCancelBtn(obj); + else + return NULL; + } else if (strncmp(part,"elm.icon.1", strlen("elm.icon.1")) == 0 || + strncmp(part, "elm.icon", strlen("elm.icon")) == 0) { +// if (strncmp(part,"elm.icon.1", strlen("elm.icon.1")) == 0) { + Evas_Object *icon = elm_icon_add(obj); + elm_icon_file_set(icon, getIconPath(), NULL); + evas_object_size_hint_aspect_set(icon, EVAS_ASPECT_CONTROL_VERTICAL,1,1); + return icon; + } else if (strcmp(part,"elm.swallow.progress") == 0) { + return createProgressBar(obj); + } else { + DP_LOGE("Cannot enter here"); + return NULL; + } +} + +void ViewItem::checkChangedCB(void *data, Evas_Object *obj, + void *event_info) +{ + DownloadView &view = DownloadView::getInstance(); + DP_LOGD_FUNC(); + //ViewItem *item = static_cast(data); + //DP_LOGD("checked[%d] viewItem[%p]",(bool)(item->checkedValue()),item); + view.handleCheckedState(); +} + +void ViewItem::clickedDeleteButton() +{ + DP_LOGD("ViewItem::clickedDeleteButton()"); + m_item->deleteFromDB(); + destroy(); +} + +void ViewItem::clickedCancelButton() +{ + DP_LOG("ViewItem::clickedCancelButton()"); + requestCancel(); +} + +void ViewItem::requestCancel() +{ + if (m_item) { + m_item->cancel(); + } +} + +void ViewItem::clickedRetryButton() +{ + DP_LOG_FUNC(); + retryViewItem(); +} + +void ViewItem::clickedGenlistItem() +{ + DownloadView &view = DownloadView::getInstance(); + DP_LOG_FUNC(); + if (!m_item) { + DP_LOGE("m_item is NULL"); + return; + } + if (view.isGenlistEditMode()) { + m_checked = !m_checked; + if (m_checkedBtn) + elm_genlist_item_fields_update(genlistItem(),"elm.edit.icon.1", + ELM_GENLIST_ITEM_FIELD_CONTENT); + else + DP_LOGE("m_checkedBtn is NULL"); + view.handleCheckedState(); + } else if (state() == ITEM::FINISH_DOWNLOAD) { + bool ret = m_item->play(); + if (ret == false) { + string desc = __("IDS_BR_POP_UNABLE_TO_OPEN_FILE"); + view.showErrPopup(desc); + } + } else if (isFinishedWithErr()) { + retryViewItem(); + } + elm_genlist_item_selected_set(genlistItem(), EINA_FALSE); +} + +Elm_Genlist_Item_Class *ViewItem::elmGenlistStyle() +{ + /* Change the genlist style class in case of download history item */ + if (state() == ITEM::FINISH_DOWNLOAD) + return &dldHistoryGenlistStyle; + else if (isFinishedWithErr()) + return &dldGenlistSlideStyle; + else + return &dldGenlistStyle; +} + +const char *ViewItem::getMessage() +{ + DP_LOGD("ViewItem state() ITEM::[%d]", state()); + const char *buff = NULL; + switch(state()) { + case ITEM::IDLE: + case ITEM::REQUESTING: + case ITEM::PREPARE_TO_RETRY: + case ITEM::WAITING_USER_RESPONSE: + case ITEM::RECEIVING_DOWNLOAD_INFO: + /* Do not display string and show only the progress bar */ +// buff = __("Check for download"); + buff = ""; + break; + case ITEM::DOWNLOADING: + buff = getHumanFriendlyBytesStr(receivedFileSize(), true); +// DP_LOGD("%s", buff); + break; + case ITEM::CANCEL: + buff = S_("IDS_COM_POP_CANCELLED"); + break; + case ITEM::FAIL_TO_DOWNLOAD: + buff = getErrMsg(); + break; + case ITEM::REGISTERING_TO_SYSTEM: + buff = S_("IDS_COM_POP_INSTALLING_ING"); + break; + case ITEM::ACTIVATING: + buff = S_("IDS_COM_POP_ACTIVATING"); + break; + case ITEM::NOTIFYING_TO_SERVER: + buff = __("IDS_BR_BODY_NOTIFYING_ING"); + break; + case ITEM::PROCESSING_DOMAIN: + buff = S_("IDS_COM_POP_PROCESSING"); + break; + case ITEM::FINISH_PROCESSING_DOMAIN: + buff = __("IDS_BR_BODY_PROCESSING_COMPLETED"); + break; + case ITEM::FINISH_DOWNLOAD: + buff = __("IDS_EMAIL_BODY_COMPLETE"); + break; + default: + buff = ""; + break; + } + return buff; +} + +const char *ViewItem::getHumanFriendlyBytesStr(unsigned long int bytes, + bool progressOption) +{ + double doubleTypeBytes = 0.0; + const char *unitStr[4] = {"B", "KB", "MB", "GB"}; + int unit = 0; + unsigned long int unitBytes = bytes; + + /* using bit operation to avoid floating point arithmetic */ + for (unit=0; (unitBytes > 1024 && unit < 4) ; unit++) { + unitBytes = unitBytes >> 10; + } + + unitBytes = 1 << (10*unit); + doubleTypeBytes = ((double)bytes / (double)(unitBytes)); + // FIXME following code should be broken into another function, but leave it now to save function call time.s + char str[32] = {0}; + if (progressOption && fileSize() != 0) { + /* using fixed point arithmetic to avoid floating point arithmetic */ + const int fixed_point = 6; + unsigned long long int receivedBytes = receivedFileSize() << fixed_point; + unsigned long long int result = (receivedBytes*100) / fileSize(); + unsigned long long int result_int = result >> fixed_point; + unsigned long long int result_fraction = result & + ~(0xFFFFFFFF << fixed_point); + if (unit == 0) + snprintf(str, sizeof(str), "%lu %s / %llu.%.2llu %%", + bytes, unitStr[unit], result_int, result_fraction); + else + snprintf(str, sizeof(str), "%.2f %s / %llu.%.2llu %%", + doubleTypeBytes, unitStr[unit], result_int, result_fraction); + } else { + if (unit == 0) + snprintf(str, sizeof(str), "%lu %s", bytes, unitStr[unit]); + else + snprintf(str, sizeof(str), "%.2f %s", doubleTypeBytes, unitStr[unit]); + } + return string(str).c_str(); +} + +unsigned long int ViewItem::receivedFileSize() +{ + if (m_item) + return m_item->receivedFileSize(); + + return 0; +} + +unsigned long int ViewItem::fileSize() +{ + if (m_item) + return m_item->fileSize(); + + return 0; +} + +const char *ViewItem::getTitle() +{ + const char *title = NULL; + if (m_item) + title = m_item->title().c_str(); + + if (!title) + return S_("IDS_COM_BODY_NO_NAME"); + + return title; +} + +Evas_Object *ViewItem::createProgressBar(Evas_Object *parent) +{ + Evas_Object *progress = NULL; + if (!parent) { + DP_LOGE("parent is NULL"); + return NULL; + } + progress = elm_progressbar_add(parent); + setProgressBar(progress); + if (isFinished()) { + DP_LOGE("Cannot enter here. finished item has othere genlist style"); + return NULL; + } + + if (fileSize() == 0 || isPreparingDownload()) { + //DP_LOGD("Pending style::progressBar[%p]",progress); + elm_object_style_set(progress, "pending_list"); + elm_progressbar_horizontal_set(progress, EINA_TRUE); + evas_object_size_hint_align_set(progress, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(progress, EVAS_HINT_EXPAND, + EVAS_HINT_EXPAND); + elm_progressbar_pulse(progress, EINA_TRUE); + } else { + //DP_LOGD("List style::progressBar[%p] fileSize[%d] state[%d]",progress, fileSize(),state()); + elm_object_style_set(progress, "list_progress"); + elm_progressbar_horizontal_set(progress, EINA_TRUE); + + if (isCompletedDownload()) + elm_progressbar_value_set(progress, 1.0); + /* When realized event is happened, the progress is created. + This is needed for that case */ + else if (state() == ITEM::DOWNLOADING) { + double percentageProgress = 0.0; + percentageProgress = (double)(receivedFileSize()) / + (double)(fileSize()); + elm_progressbar_value_set(progress, percentageProgress); + } + } + evas_object_show(progress); + return progress; +} + +void ViewItem::updateCheckedBtn() +{ + if (m_checkedBtn) + elm_check_state_pointer_set(m_checkedBtn,&m_checked); +} + +void ViewItem::deleteBtnClickedCB(void *data, Evas_Object *obj, void *event_info) +{ + DP_LOGD_FUNC(); + if (!data) { + DP_LOGE("data is NULL"); + return; + } + ViewItem *viewItem = static_cast(data); + viewItem->clickedDeleteButton(); +} + +void ViewItem::retryBtnClickedCB(void *data, Evas_Object *obj, void *event_info) +{ + DP_LOGD_FUNC(); + if (!data) { + DP_LOGE("data is NULL"); + return; + } + ViewItem *viewItem = static_cast(data); + viewItem->clickedRetryButton(); +} + +Evas_Object *ViewItem::createCancelBtn(Evas_Object *parent) +{ + DP_LOGD_FUNC(); + Evas_Object *button = elm_button_add(parent); + elm_object_part_content_set(parent, "btn_style1", button); + elm_object_style_set(button, "style1/auto_expand"); + evas_object_size_hint_aspect_set(button, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + elm_object_text_set(button, S_("IDS_COM_SK_CANCEL")); + evas_object_propagate_events_set(button, EINA_FALSE); + evas_object_smart_callback_add(button,"clicked", cancelBtnClickedCB, this); + return button; +} + +void ViewItem::cancelBtnClickedCB(void *data, Evas_Object *obj, void *event_info) +{ + DP_LOGD_FUNC(); + if (!data) { + DP_LOGE("data is NULL"); + return; + } + ViewItem *viewItem = static_cast(data); + viewItem->clickedCancelButton(); +} + +void ViewItem::extractDateGroupType() +{ + DP_LOGD_FUNC(); + /* History Item */ + //DP_LOGD("state[%s],finishedTime[%ld]",stateStr(),finishedTime()); + if (isFinished() && finishedTime() > 0) { + int diffDay = 0; + DateUtil &inst = DateUtil::getInstance(); + double nowTime = inst.nowTime(); + double finishTime = finishedTime(); + diffDay = inst.getDiffDays((time_t)nowTime, (time_t)finishTime); + if (diffDay == 0) + m_dateGroupType = DATETIME::DATE_TYPE_TODAY; + else if (diffDay == 1) + m_dateGroupType = DATETIME::DATE_TYPE_YESTERDAY; + else if (diffDay > 1) + m_dateGroupType = DATETIME::DATE_TYPE_PREVIOUS; + else + m_dateGroupType = DATETIME::DATE_TYPE_LATER; + return; + } + /* Item which is added now or retrying item */ + m_dateGroupType = DATETIME::DATE_TYPE_TODAY; +} + + +void ViewItem::retryViewItem(void) +{ + DownloadView &view = DownloadView::getInstance(); + DP_LOGD_FUNC(); + if (m_item) { + m_isRetryCase = true; + m_item->clearForRetry(); + if (!m_item->retry()) { + DownloadView &view = DownloadView::getInstance(); + string desc = S_("IDS_COM_POP_FAILED"); + view.showErrPopup(desc); + m_item->deleteFromDB(); + m_item->destroy(); + return; + } + /* Move a item to Today group, if it is not included to Today group */ + view.moveRetryItem(this); + } +} diff --git a/src/include/download-provider-common.h b/src/include/download-provider-common.h new file mode 100644 index 0000000..4131c0d --- /dev/null +++ b/src/include/download-provider-common.h @@ -0,0 +1,103 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-common.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Common define and data + */ + +#ifndef DOWNLOAD_PROVIDER_DOWNLOAD_COMMON_H +#define DOWNLOAD_PROVIDER_DOWNLOAD_COMMON_H + +#include +#include "download-provider-debug.h" + +#if !defined(PACKAGE) + #define PACKAGE "download-provider" +#endif + +#define _EDJ(o) elm_layout_edje_get(o) +#define __(s) dgettext(PACKAGE, s) +#define S_(s) dgettext("sys_string", s) + +#define ERROR_POPUP_LOW_MEM S_("IDS_COM_POP_NOT_ENOUGH_MEMORY") +#define ERROR_POPUP_UNKNOWN S_("IDS_COM_POP_INTERNAL_ERROR") +#define ERROR_POPUP_INVALID_URL S_("IDS_COM_POP_INVALID_URL") + +#define DP_DRM_ICON_PATH IMAGEDIR"/U06_icon_DRM.png" +#define DP_JAVA_ICON_PATH IMAGEDIR"/U06_icon_Java.png" +#define DP_UNKNOWN_ICON_PATH IMAGEDIR"/U06_icon_Unknown.png" +#define DP_EXCEL_ICON_PATH IMAGEDIR"/U06_icon_excel.png" +#define DP_HTML_ICON_PATH IMAGEDIR"/U06_icon_html.png" +#define DP_MUSIC_ICON_PATH IMAGEDIR"/U06_icon_music.png" +#define DP_PDF_ICON_PATH IMAGEDIR"/U06_icon_pdf.png" +#define DP_PPT_ICON_PATH IMAGEDIR"/U06_icon_ppt.png" +#define DP_RINGTONE_ICON_PATH IMAGEDIR"/U06_icon_ringtone.png" +#define DP_TEXT_ICON_PATH IMAGEDIR"/U06_icon_text.png" +#define DP_WORD_ICON_PATH IMAGEDIR"/U06_icon_word.png" +#define DP_VIDEO_ICON_PATH IMAGEDIR"/U06_icon_video.png" +#define DP_IMAGE_ICON_PATH IMAGEDIR"/U06_icon_image.png" + +#define MAX_FILE_PATH_LEN 256 +#define MAX_BUF_LEN 256 + +#define LOAD_HISTORY_COUNT 500 + +enum +{ + DP_CONTENT_NONE = 0, + DP_CONTENT_IMAGE, + DP_CONTENT_VIDEO, + DP_CONTENT_MUSIC, + DP_CONTENT_PDF, + DP_CONTENT_WORD, + DP_CONTENT_PPT, // 5 + DP_CONTENT_EXCEL, + DP_CONTENT_HTML, + DP_CONTENT_TEXT, + DP_CONTENT_RINGTONE, + DP_CONTENT_DRM, // 10 + DP_CONTENT_JAVA, + DP_CONTENT_SVG, + DP_CONTENT_FLASH, + DP_CONTENT_UNKOWN +}; + +namespace DL_TYPE{ +enum TYPE { + TYPE_NONE, + HTTP_DOWNLOAD, + OMA_DOWNLOAD, + MIDP_DOWNLOAD +}; +} + +namespace ERROR { +enum CODE { + NONE, + INVALID_URL, + NETWORK_FAIL, + NOT_ENOUGH_MEMORY, + FAIL_TO_INSTALL, + FAIL_TO_PARSE_DESCRIPTOR, + OMA_POPUP_TIME_OUT, + ENGINE_FAIL, + UNKNOWN +}; +} + +#endif /* DOWNLOAD_PROVIDER_DOWNLOAD_COMMON_H */ diff --git a/src/include/download-provider-dateTime.h b/src/include/download-provider-dateTime.h new file mode 100644 index 0000000..87caf11 --- /dev/null +++ b/src/include/download-provider-dateTime.h @@ -0,0 +1,111 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-dateTime.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief data and utility APIs for Date and Time + */ + +#ifndef DOWNLOAD_PROVIDER_DATE_TIME_H +#define DOWNLOAD_PROVIDER_DATE_TIME_H + +#include +#include +#include +#include +#include + +#include "download-provider-common.h" + +using namespace std; + +namespace DATETIME { +enum { + DATE_TYPE_NONE = 0, + DATE_TYPE_LATER, + DATE_TYPE_TODAY, + DATE_TYPE_YESTERDAY, + DATE_TYPE_PREVIOUS, +}; +} + +namespace LOCALE_STYLE{ +enum { + TIME = 0, + SHORT_DATE, + MEDIUM_DATE, + FULL_DATE +}; +} + +class DateGroup { +public: + DateGroup(void); + ~DateGroup(void); + + Elm_Object_Item *glGroupItem() { return m_glGroupItem; } + void setGlGroupItem(Elm_Object_Item *i) { m_glGroupItem = i; } + void increaseCount(void) { count++; } + void decreaseCount(void) { count--; } + int getCount(void) { return count; } + void initData(void); + void setType(int t) { type = t; } + int getType(void) { return type; } + +private: + int count; + int type; + Elm_Object_Item *m_glGroupItem; +}; + +class DateUtil { +public: + static DateUtil& getInstance(void) { + static DateUtil inst; + return inst; + } + + inline void setTodayStandardTime(void) { m_todayStandardTime = time(NULL); } + int getDiffDaysFromToday(void); + int getDiffDays(time_t nowTime, time_t refTime); + void updateLocale(void); + void getDateStr(int style, double time, string &outBuf); + inline double nowTime(void) { return (double)(time(NULL)); } + /* yesterday is same to 24*60*60 seconds from now */ + inline double yesterdayTime(void) { return (double)(time(NULL)+24*60*60); } + +private: + DateUtil(void); + ~DateUtil(void); + + UDateFormat *getBestPattern(const char *patternStr, + UDateTimePatternGenerator *generator, const char *locale); + void deinitLocaleData(void); + /* Update this in case of follows + * 1. show main view. + * 2. add new item + * 3. create today group + **/ + time_t m_todayStandardTime; + UDateFormat *dateShortFormat; + UDateFormat *dateMediumFormat; + UDateFormat *dateFullFormat; + UDateFormat *timeFormat12H; + UDateFormat *timeFormat24H; +}; + +#endif /* DOWNLOAD_PROVIDER_DATE_TIME_H */ diff --git a/src/include/download-provider-debug.h b/src/include/download-provider-debug.h new file mode 100644 index 0000000..4c4552b --- /dev/null +++ b/src/include/download-provider-debug.h @@ -0,0 +1,76 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-debug.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief debug function + */ + +#ifndef DOWNLOAD_PROVIDER_DEBUG_H +#define DOWNLOAD_PROVIDER_DEBUG_H + +#define _USE_DLOG 1 + +#ifdef _USE_DLOG +#include + +#ifdef LOG_TAG +#undef LOG_TAG +#endif + +#define LOG_TAG "DownloadProvider" + +#define DP_LOG(format, args...) LOGI("[%s] "format, __func__, ##args) +#define DP_LOGD(format, args...) LOGD("[%s] "format, __func__, ##args) +#define DP_LOG_START(msg) LOGI("<<= [%s] Start =>>\n",msg) +#define DP_LOG_FUNC() LOGI("<<= [%s]=>>\n",__func__) +#define DP_LOGD_FUNC() LOGD("<<= [%s]=>>\n",__func__) +#define DP_LOG_END(msg) LOGI("<<= [%s] End [%d] =>>\n",msg) +#define DP_LOGE(format, args...) LOGE("[%s][ERR] "format, __func__, ##args) +#define DP_LOG_TEST(format, args...) LOGI("####TEST####[%s] "format, __func__, ##args) + +#else + +#include +#include + +#define DP_LOG(args...) do {\ + printf("[DP:%s][LN:%d][%lu]",__func__,__LINE__,pthread_self());\ + printf(args);printf("\n"); }while(0) +#define DP_LOGD(args...) do {\ + printf("[DP_D:%s][LN:%d][%lu]",__func__,__LINE__,pthread_self());\ + printf(args);printf("\n");}while(0) +#define DP_LOGE(args...) do {\ + printf("[DP_ERR:%s][LN:%d][%lu]",__func__,__LINE__,pthread_self());\ + printf(args);printf("\n");}while(0) +#define DP_LOG_FUNC() do {\ + printf("<<==[DP:%s][LN:%d][%lu] ==>> \n",__func__,__LINE__,pthread_self());\ + }while(0) +#define DP_LOGD_FUNC() do {\ + printf("<<==[DP_D:%s][LN:%d][%lu] ==>> \n",__func__,__LINE__,pthread_self());\ + }while(0) +#define DP_LOG_START(msg) do {\ + printf("<<==[DP:%s][LN:%d][%lu] Start ==>> \n",\ + __FUNCTION__,__LINE__,pthread_self());\ + }while(0) +#define DP_LOG_END(msg) do {\ + printf("<<==[DP:%s][LN:%d][%lu] End ==>> \n",\ + __FUNCTION__,__LINE__,pthread_self());\ + }while(0) +#endif /*_USE_DLOG*/ + +#endif /* DOWNLOAD_PROVIDER_DEBUG_H */ diff --git a/src/include/download-provider-downloadItem.h b/src/include/download-provider-downloadItem.h new file mode 100644 index 0000000..9421246 --- /dev/null +++ b/src/include/download-provider-downloadItem.h @@ -0,0 +1,140 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-downloadItem.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief download item class + */ + +#ifndef DOWNLOAD_PROVIDER_DOWNLOAD_ITEM_H +#define DOWNLOAD_PROVIDER_DOWNLOAD_ITEM_H + +#include "download-provider-common.h" +#include "download-provider-downloadRequest.h" +#include "download-provider-event.h" +#include "download-agent-interface.h" +#include + +namespace DL_ITEM { +enum STATE { + IGNORE, + STARTED, + WAITING_CONFIRM, + UPDATING, + COMPLETE_DOWNLOAD, + INSTALL_NOTIFY, + START_DRM_DOMAIN, + FINISH_DRM_DOMAIN, + WAITING_RO, + SUSPENDED, + RESUMED, + FINISHED, + CANCELED, + FAILED +}; +} + +class DownloadItem { +public: + DownloadItem(); /* FIXME remove after cleanup ecore_pipe */ + DownloadItem(auto_ptr request); + ~DownloadItem(); + + void start(void); + void cancel(void); + void retry(void); + bool sendUserResponse(bool res); + void suspend(void); + void resume(void); + + inline int downloadId(void) { return m_da_req_id;} + inline void setDownloadId(int id) { m_da_req_id = id; } + + inline unsigned long int receivedFileSize(void) { return m_receivedFileSize; } + inline void setReceivedFileSize(unsigned long int size) { m_receivedFileSize = size; } + + inline unsigned long int fileSize(void) { return m_fileSize; } + inline void setFileSize(unsigned long int size) { m_fileSize = size; } + + inline string &filePath(void) { return m_filePath; } + inline void setFilePath(const char *path) { if (path) m_filePath = path; } + inline void setFilePath(string &path) { m_filePath = path; } + + inline string ®isteredFilePath(void) { return m_registeredFilePath; } + inline void setRegisteredFilePath(string &path) { m_registeredFilePath = path; } + + inline string &mimeType(void) { return m_mimeType; } + inline void setMimeType(const char *mime) { m_mimeType = mime; } + inline void setMimeType(string &mime) { m_mimeType = mime; } + + inline DL_ITEM::STATE state(void) { return m_state; } + inline void setState(DL_ITEM::STATE state) { m_state = state; } + + inline ERROR::CODE errorCode(void) { return m_errorCode; } + inline void setErrorCode(ERROR::CODE err) { m_errorCode = err; } + inline bool isMidletInstalled(void) { return m_isMidletInstalled; } + inline void setIsMidletInstalled(bool b) { m_isMidletInstalled = b; } + inline DL_TYPE::TYPE downloadType(void) { return m_downloadType; } + inline void setDownloadType(DL_TYPE::TYPE t) { m_downloadType = t;} + inline string &contentName(void) { return m_contentName; } + inline void setContentName(string &name) { m_contentName = name; } + inline string &vendorName(void) { return m_vendorName; } + inline void setVendorName(string &name) { m_vendorName = name; } + + inline void notify(void) { m_subject.notify(); } + inline void subscribe(Observer *o) { if (o) m_subject.attach(o); } + inline void deSubscribe(Observer *o) { if (o) m_subject.detach(o); } + inline string &url(void) { return m_aptr_request->getUrl(); } + inline string &cookie(void) { return m_aptr_request->getCookie(); } + + DL_ITEM::STATE _convert_da_state_to_download_state(int da_state); + ERROR::CODE _convert_da_error(int da_err); + +private: + auto_ptr m_aptr_request; + Subject m_subject; + da_handle_t m_da_req_id; + DL_ITEM::STATE m_state; + ERROR::CODE m_errorCode; + unsigned long int m_receivedFileSize; + unsigned long int m_fileSize; + string m_filePath; + string m_registeredFilePath; + string m_mimeType; + DL_TYPE::TYPE m_downloadType; + bool m_isMidletInstalled; /* For MIDP */ + string m_contentName; /* For OMA & MIDP */ + string m_vendorName; /* For MIDP */ +}; + +class DownloadEngine { +public: + static DownloadEngine &getInstance(void) { + static DownloadEngine downloadEngine; + return downloadEngine; + } + + void initEngine(void); + void deinitEngine(void); +private: + DownloadEngine(void); + ~DownloadEngine(void); + +}; + + +#endif /* DOWNLOAD_PROVIDER_DOWNLOAD_ITEM_H */ diff --git a/src/include/download-provider-downloadRequest.h b/src/include/download-provider-downloadRequest.h new file mode 100644 index 0000000..a21f7df --- /dev/null +++ b/src/include/download-provider-downloadRequest.h @@ -0,0 +1,49 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-downloadRequest.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Download Request class + */ + +#ifndef DOWNLOAD_PROVIDER_DOWNLOAD_REQUEST_H +#define DOWNLOAD_PROVIDER_DOWNLOAD_REQUEST_H + +#include + +using namespace std; + +class DownloadRequest +{ +public: +// DownloadRequest(); + DownloadRequest(string url, string cookie); + DownloadRequest(DownloadRequest &rRequest); + ~DownloadRequest(); + + string &getUrl(); + string &getCookie(); + bool isUrlEmpty(); + bool isCookieEmpty(); + void setUrl(string url); + void setCookie(string cookie); +private: + string m_url; + string m_cookie; +}; + +#endif /* DOWNLOAD_PROVIDER_DOWNLOAD_REQUEST_H */ diff --git a/src/include/download-provider-event.h b/src/include/download-provider-event.h new file mode 100644 index 0000000..e9378a6 --- /dev/null +++ b/src/include/download-provider-event.h @@ -0,0 +1,72 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-event.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Download event class + */ +#ifndef DOWNLOAD_PROVIDER_EVENT_H +#define DOWNLOAD_PROVIDER_EVENT_H + +#include +/* For debug */ +#include + +using namespace std; + +class Observer; +class Subject +{ +public: + Subject(){} + ~Subject(){} + + void attach(Observer *); + void detach(Observer *); + void notify(void); + +private: + vector _observers; +}; + +typedef void (*updateFunction)(void *data); + +class Observer +{ +public: + /* For debug */ + Observer(updateFunction uf, void *data, const char *name); + //Observer(updateFunction uf, void *data); + ~Observer(){} + + void update(Subject *s); + void set(updateFunction uf, void *data); + void clear(void); + void *getUserData(void) { return m_userData; } + /* For debug */ + string name(void) { return observerName; } + +private: + void call(void); + + updateFunction m_updateFunction; + void *m_userData; + /* For debug */ + string observerName; +}; + +#endif /* DOWNLOAD_PROVIDER_EVENT_H */ diff --git a/src/include/download-provider-history-db.h b/src/include/download-provider-history-db.h new file mode 100644 index 0000000..b22883e --- /dev/null +++ b/src/include/download-provider-history-db.h @@ -0,0 +1,56 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-history-db.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Manager for a download history DB + */ + +#ifndef DOWNLOAD_PROVIDER_HISTORY_DB_H +#define DOWNLOAD_PROVIDER_HISTORY_DB_H + +#include +#include +#include +#include "download-provider-item.h" +extern "C" { +#include +} + +using namespace std; + +class DownloadHistoryDB +{ +public: + static bool addToHistoryDB(Item *item); + static bool createRemainedItemsFromHistoryDB(int limit, int offset); + static bool createItemsFromHistoryDB(void); + static bool deleteItem(unsigned int historyId); + static bool deleteMultipleItem(queue &q); + static bool clearData(void); + static bool getCountOfHistory(int *count); +private: + DownloadHistoryDB(void); + ~DownloadHistoryDB(void); + static sqlite3* historyDb; + static bool open(void); + static bool isOpen(void) { return historyDb ? true : false; } + static void close(void); +}; + +#endif /* DOWNLOAD_PROVIDER_HISTORY_DB_H */ + diff --git a/src/include/download-provider-item.h b/src/include/download-provider-item.h new file mode 100644 index 0000000..65ab1eb --- /dev/null +++ b/src/include/download-provider-item.h @@ -0,0 +1,204 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-item.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Item class + */ +#ifndef DOWNLOAD_PROVIDER_ITEM_H +#define DOWNLOAD_PROVIDER_ITEM_H + +#include +#include +#include "download-provider-event.h" +#include "download-provider-downloadRequest.h" +#include "download-provider-downloadItem.h" +#include "download-provider-util.h" + +using namespace std; + +namespace ITEM { +enum STATE { + IDLE, + REQUESTING, + PREPARE_TO_RETRY, + WAITING_USER_RESPONSE, + RECEIVING_DOWNLOAD_INFO, + DOWNLOADING, + REGISTERING_TO_SYSTEM, + PROCESSING_DOMAIN, + FINISH_PROCESSING_DOMAIN, + ACTIVATING, + NOTIFYING_TO_SERVER, + SUSPEND, + FINISH_DOWNLOAD, + FAIL_TO_DOWNLOAD, + CANCEL, + PLAY, + DESTROY +}; +} + +class DownloadNoti; + +class Item { +public: + static void create(DownloadRequest &rRequest); + static Item *createHistoryItem(void); + ~Item(void); + + void attachHistoryItem(void); + void destroy(void); + /* SHOULD call this before destrying an item*/ + void deleteFromDB(void); + void download(void); + inline void cancel(void) + { + if (m_aptr_downloadItem.get()) + m_aptr_downloadItem->cancel(); + return; + } + void clearForRetry(void); + bool retry(void); + + void sendUserResponse(bool res); + bool play(void); + + inline void subscribe(Observer *o) { m_subjectForView.attach(o); } + inline void deSubscribe(Observer *o) { m_subjectForView.detach(o); } + + static void updateCBForDownloadObserver(void *data); + static void netEventCBObserver(void *data); + void updateFromDownloadItem(void); + inline void suspend(void) { m_aptr_downloadItem->suspend(); } + + inline int id(void) { + if (m_aptr_downloadItem.get()) + return m_aptr_downloadItem->downloadId(); + + return -1; + } // FIXME create Item's own id + + inline unsigned long int receivedFileSize(void) { + if (m_aptr_downloadItem.get()) + return m_aptr_downloadItem->receivedFileSize(); + return 0; + } + + inline unsigned long int fileSize(void) { + if (m_aptr_downloadItem.get()) + return m_aptr_downloadItem->fileSize(); + return 0; + } + + inline string &filePath(void) { + if (m_aptr_downloadItem.get()) + return m_aptr_downloadItem->filePath(); + return m_emptyString; + } + + inline bool isMidletInstalled(void) { + if (m_aptr_downloadItem.get()) + return m_aptr_downloadItem->isMidletInstalled(); + return false; + } + + inline void setHistoryId(unsigned int i) { m_historyId = i; } + inline unsigned int historyId(void) { return m_historyId; } // FIXME duplicated with m_id + inline string &title(void) {return m_title;} + inline void setTitle(string &title) { m_title = title; } + string &contentName(void); + inline void setContentName(string &c) { m_contentName = c; } + string &vendorName(void); + inline void setVendorName(string &v) { m_vendorName = v; } + string ®isteredFilePath(void); + inline void setRegisteredFilePath(string &r) { m_registeredFilePath = r; } + string &url(void); + string &cookie(void); + void setRetryData(string &url, string &cookie); + int contentType(void) { return m_contentType; } + inline void setContentType(int t) { m_contentType = t; } + DL_TYPE::TYPE downloadType(void); + inline void setDownloadType(DL_TYPE::TYPE t) { m_downloadType = t; } + +// string &getIconPath(void) {return m_iconPath; } + inline string &iconPath(void) { return m_iconPath; } + + inline void setState(ITEM::STATE state) { m_state = state; } + inline ITEM::STATE state(void) { return m_state; } + + inline void setErrorCode(ERROR::CODE err) { m_errorCode = err; } + inline ERROR::CODE errorCode(void) { return m_errorCode; } + const char *getErrorMessage(void); + inline void setFinishedTime(double t) { m_finishedTime = t; } + inline double finishedTime(void) { return m_finishedTime; } + + inline string getMidletPkgName(void) { + DownloadUtil &util = DownloadUtil::getInstance(); + return util.getMidletPkgName(m_contentName, m_vendorName); + } + + bool isFinished(void); /* include finish download state with error */ + bool isFinishedWithErr(void); + bool isPreparingDownload(void); /* Before downloading start */ + bool isCompletedDownload(void); /* After stating installation */ + + /* Test code */ + const char *stateStr(void); + +private: + Item(void); + Item(DownloadRequest &rRequest); + + inline void notify(void) { m_subjectForView.notify(); } + + void createSubscribeData(void); + void extractTitle(void); + void extractIconPath(void); + + void startUpdate(void); + void createHistoryId(void); + bool isExistedHistoryId(unsigned int id); + void handleFinishedItem(void); + + auto_ptr m_aptr_request; + auto_ptr m_aptr_downloadItem; + FileOpener m_fileOpener; + + Subject m_subjectForView; + auto_ptr m_aptr_downloadObserver; + auto_ptr m_aptr_netEventObserver; + + ITEM::STATE m_state; + ERROR::CODE m_errorCode; + string m_title; + unsigned int m_historyId; + int m_contentType; + string m_iconPath; // FIXME Later:is it right to exist here? (ViewItem or not) + string m_emptyString; // FIXME this is temporary to avoid crash when filePath() is called if m_aptr_downloaditem points nothing + double m_finishedTime; + DL_TYPE::TYPE m_downloadType; + string m_contentName; + string m_vendorName; + string m_registeredFilePath; + string m_url; + string m_cookie; + + bool m_gotFirstData; +}; + +#endif /* DOWNLOAD_PROVIDER_ITEM_H */ diff --git a/src/include/download-provider-items.h b/src/include/download-provider-items.h new file mode 100644 index 0000000..8395719 --- /dev/null +++ b/src/include/download-provider-items.h @@ -0,0 +1,45 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/* + * @file download-provider-items.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief item inventory class + */ +#ifndef DOWNLOAD_PROVIDER_ITEMS_H +#define DOWNLOAD_PROVIDER_ITEMS_H + +#include "download-provider-item.h" +#include + +class Items { +public: + static Items& getInstance(void) { + static Items inst; + return inst; + } + + void attachItem(Item *item); + void detachItem(Item *item); + bool isExistedHistoryId(unsigned int id); +private: + Items(){} + ~Items(){DP_LOGD_FUNC();} + + vector m_items; +}; + +#endif /* DOWNLOAD_PROVIDER_ITEMS_H */ diff --git a/src/include/download-provider-network.h b/src/include/download-provider-network.h new file mode 100644 index 0000000..2d0f5eb --- /dev/null +++ b/src/include/download-provider-network.h @@ -0,0 +1,57 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-network.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Download netowkr manager + */ + +#ifndef DOWNLOAD_PROVIDER_NETWORK_H +#define DOWNLOAD_PROVIDER_NETWORK_H + +#include "vconf.h" +#include "vconf-keys.h" +#include "download-provider-event.h" + +class NetMgr { +public: + static NetMgr& getInstance(void) { + static NetMgr inst; + return inst; + } + void initNetwork(void); + void deinitNetwork(void); + void netStatusChanged(void); + void netConfigChanged(void); + inline void subscribe(Observer *o) { m_subject.attach(o); } + inline void deSubscribe(Observer *o) { m_subject.detach(o); } + static void netStatusChangedCB(keynode_t *keynode, void *data); + static void netConfigChangedCB(keynode_t *keynode, void *data); +private: + NetMgr(void); + ~NetMgr(void); + int getConnectionState(void); + int getCellularStatus(void); + int getWifiStatus(void); + void getProxy(void); + void getIPAddress(void); + inline void notify() { m_subject.notify(); } + int m_netStatus; + Subject m_subject; +}; + +#endif diff --git a/src/include/download-provider-util.h b/src/include/download-provider-util.h new file mode 100644 index 0000000..0ed6575 --- /dev/null +++ b/src/include/download-provider-util.h @@ -0,0 +1,57 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/* + * @file download-provider-util.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Utility APIs and interface with content player + */ + +#ifndef DOWNLOAD_PROVIDER_UTIL_H +#define DOWNLOAD_PROVIDER_UTIL_H + +#include +#include "download-provider-common.h" + +using namespace std; +class FileOpener { +public: + FileOpener() {} + ~FileOpener() {} + + bool openFile(string &path, int contentType); + bool openApp(string &pkgName); +}; + +class DownloadUtil +{ +public: + static DownloadUtil& getInstance(void) { + static DownloadUtil inst; + return inst; + } + + string getMidletPkgName(string& name, string& vendor); + int getContentType(const char *mimem, const char *filePath); + +private: + DownloadUtil(void); + ~DownloadUtil(void) {} + void initDrm(void); + bool isAmbiguousMIMEType(const char *mimeType); +}; + +#endif//DOWNLOAD_PROVIDER_UTIL_H diff --git a/src/include/download-provider-view.h b/src/include/download-provider-view.h new file mode 100644 index 0000000..4fdfab0 --- /dev/null +++ b/src/include/download-provider-view.h @@ -0,0 +1,160 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-view.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Download UI View manager + */ + +#ifndef DOWNLOAD_PROVIDER_VIEW_H +#define DOWNLOAD_PROVIDER_VIEW_H + +#include +#include + +#include +#include "download-provider-common.h" +#include "download-provider-viewItem.h" +#include "download-provider-dateTime.h" + +enum { + POPUP_EVENT_EXIT = 0, + POPUP_EVENT_ERR, +}; + +class DownloadView { +public: + static DownloadView& getInstance(void) { + static DownloadView inst; + return inst; + } + + Evas_Object *create(void); + void createView(void); + void activateWindow(void); + void show(void); + void hide(void); + + void attachViewItem(ViewItem *viewItem); + void detachViewItem(ViewItem *viewItem); + + void changedRegion(void); + void showErrPopup(string &desc); + void showOMAPopup(string &msg, ViewItem *viewItem); + void update(); + void update(ViewItem *viewItem); + void update(Elm_Object_Item *glItem); + void showViewItem(int id, const char *title); + void playContent(int id, const char *title); + void handleChangedAllCheckedState(void); + void handleCheckedState(void); + bool isGenlistEditMode(void); + void handleGenlistGroupItem(int type); + void moveRetryItem(ViewItem *viewItem); + static char *getGenlistGroupLabelCB(void *data, Evas_Object *obj, + const char *part); + +private: + static void showNotifyInfoCB(void *data, Evas *evas, Evas_Object *obj, void *event); + static void hideNotifyInfoCB(void *data, Evas *evas, Evas_Object *obj, void *event); + static void backBtnCB(void *data, Evas_Object *obj, void *event_info); + static void cbItemDeleteCB(void *data, Evas_Object *obj, void *event_info); + static void cbItemCancelCB(void *data, Evas_Object *obj, void *event_info); + static void selectAllClickedCB(void *data, Evas *evas, Evas_Object *obj, + void *event_info); + static void selectAllChangedCB(void *data, Evas_Object *obj, + void *event_info); + static void genlistClickCB(void *data, Evas_Object *obj, void *event_info); + static void cancelClickCB(void *data, Evas_Object *obj, void *event_info); + static void errPopupResponseCB(void *data, Evas_Object *obj, void *event_info); + static void omaPopupResponseOKCB(void *data, Evas_Object *obj, void *event_info); + static void omaPopupResponseCancelCB(void *data, Evas_Object *obj, void *event_info); + +private: + DownloadView(); + ~DownloadView(); + + inline void destroyEvasObj(Evas_Object *e) { if(e) evas_object_del(e); e = NULL;} + void setTheme(void); + void setIndicator(Evas_Object *window); + Evas_Object *createWindow(const char *windowName); + Evas_Object *createBackground(Evas_Object *window); + Evas_Object *createLayout(Evas_Object *parent); + void createTheme(void); + void createNaviBar(void); + void createBackBtn(void); + void createControlBar(void); + void createBox(void); + void createList(void); + + void removeTheme(void); + + void addViewItemToGenlist(ViewItem *viewItem); + void createGenlistItem(ViewItem *viewItem); + void showEmptyView(void); + void hideEmptyView(void); + + void removePopup(void); + void showGenlistEditMode(void); + void hideGenlistEditMode(void); + void createSelectAllLayout(void); + void changeAllCheckedValue(void); + void destroyCheckedItem(void); + void showNotifyInfo(int type, int selectedCount); + void destroyNotifyInfo(void); + void createNotifyInfo(void); + + DateGroup *getDateGroupObj(int type); + Elm_Object_Item *getGenlistGroupItem(int type); + int getGenlistGroupCount(int type); + void setGenlistGroupItem(int type, Elm_Object_Item *item); + void increaseGenlistGroupCount(int type); + void handleUpdateDateGroupType(ViewItem *viewItem); + void cleanGenlistData(); + char *getGenlistGroupLabel(void *data, Evas_Object *obj, const char *part); + + Evas_Object *eoWindow; + Evas_Object *eoBackground; + Evas_Object *eoLayout; + Elm_Theme *eoTheme; + + Evas_Object *eoEmptyNoContent; + Evas_Object *eoNaviBar; + Elm_Object_Item *eoNaviBarItem; + Evas_Object *eoBackBtn; + Evas_Object *eoControlBar; + Elm_Object_Item *eoCbItemDelete; + Elm_Object_Item *eoCbItemCancel; + Elm_Object_Item *eoCbItemEmpty; + Evas_Object *eoBoxLayout; + Evas_Object *eoBox; + Evas_Object *eoDldList; + Evas_Object *eoPopup; + Evas_Object *eoSelectAllLayout; + Evas_Object *eoAllCheckedBox; + Evas_Object *eoNotifyInfo; + Evas_Object *eoNotifyInfoLayout; + Elm_Genlist_Item_Class dldGenlistGroupStyle; + Eina_Bool m_allChecked; + + int m_viewItemCount; + DateGroup m_today; + DateGroup m_yesterday; + DateGroup m_previousDay; +}; + +#endif /* DOWNLOAD_PROVIDER_VIEW_H */ diff --git a/src/include/download-provider-viewItem.h b/src/include/download-provider-viewItem.h new file mode 100644 index 0000000..70e8ec5 --- /dev/null +++ b/src/include/download-provider-viewItem.h @@ -0,0 +1,136 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file download-provider-viewItem.h + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief Item class for Download view + */ + +#ifndef DOWNLOAD_PROVIDER_VIEW_ITEM_H +#define DOWNLOAD_PROVIDER_VIEW_ITEM_H + +#include "download-provider-event.h" +#include "download-provider-item.h" +#include +#include + +using namespace std; + +class ViewItem { +public: + ~ViewItem(); + static void create(Item *item); + void destroy(void); + inline void deleteFromDB(void) { m_item->deleteFromDB(); } + + inline void setItem(Item *item) { m_item = item; } + static void updateCB(void *); + + + static char *getGenlistLabelCB(void *data, Evas_Object *obj, + const char *part); + char *getGenlistLabel(Evas_Object *obj, const char *part); + + static Evas_Object *getGenlistIconCB(void *data, Evas_Object *obj, + const char *part); + Evas_Object *getGenlistIcon(Evas_Object *obj, const char *part); + + static void checkChangedCB(void *data, Evas_Object *obj, void *event_info); + + const char *getMessage(void); + const char *getBytesStr(void); + const char *getHumanFriendlyBytesStr(unsigned long int bytes, + bool progressOption); + + Elm_Genlist_Item_Class *elmGenlistStyle(void); + + inline Elm_Genlist_Item_Class *elmGenlistItemClass(void) + { return &dldGenlistStyle; } + inline Elm_Genlist_Item_Class *elmGenlistHistoryItemClass(void) + { return &dldHistoryGenlistStyle; } + inline Elm_Genlist_Item_Class *elmGenlistFailedItemClass(void) + { return &dldGenlistSlideStyle; } + inline ITEM::STATE state(void) { return m_item->state(); } + inline const char* stateStr(void) { return m_item->stateStr(); } + inline bool isFinished(void) { return m_item->isFinished(); } + inline bool isFinishedWithErr(void) { return m_item->isFinishedWithErr(); } + inline bool isPreparingDownload(void) { return m_item->isPreparingDownload(); } + inline bool isCompletedDownload(void) { return m_item->isCompletedDownload(); } + + unsigned long int receivedFileSize(void); + unsigned long int fileSize(void); + const char *getTitle(void); + inline const char *getErrMsg(void) { return m_item->getErrorMessage(); } + const char *getIconPath(void) { return m_item->iconPath().c_str(); } + + inline Elm_Object_Item *genlistItem(void) { return m_glItem; } + inline void setGenlistItem(Elm_Object_Item *glItem) { m_glItem = glItem; } + inline void setProgressBar(Evas_Object *p) { m_progressBar = p; } + + void clickedDeleteButton(void); + void clickedCancelButton(void); + void clickedRetryButton(void); + void clickedGenlistItem(void); + void requestCancel(void); + inline void sendUserResponse(bool res) + { + return m_item->sendUserResponse(res); + } + inline Eina_Bool checkedValue(void) { return m_checked; } + void setCheckedValue(Eina_Bool b) { m_checked = b; } + inline Evas_Object *checkedBtn(void) { return m_checkedBtn; } + void setCheckedBtn(Evas_Object *e) { m_checkedBtn = e; } + + void updateCheckedBtn(void); + + inline int dateGroupType(void) { return m_dateGroupType; } + void setDateGroupType (int t) { m_dateGroupType = t; } + + inline double finishedTime(void) { return m_item->finishedTime();} + void extractDateGroupType(void); + + inline unsigned int historyId(void) { return m_item->historyId(); } +private: + ViewItem(Item *item); + + void updateFromItem(void); + Evas_Object *createProgressBar(Evas_Object *parent); + Evas_Object *createCancelBtn(Evas_Object *parent); + void retryViewItem(void); + + static void deleteBtnClickedCB(void *data, Evas_Object *obj, + void *event_info); + static void cancelBtnClickedCB(void *data, Evas_Object *obj, + void *event_info); + static void retryBtnClickedCB(void *data, Evas_Object *obj, + void *event_info); + + auto_ptr m_aptr_observer; + Item *m_item; + + Elm_Genlist_Item_Class dldGenlistStyle; + Elm_Genlist_Item_Class dldHistoryGenlistStyle; + Elm_Genlist_Item_Class dldGenlistSlideStyle; + Elm_Object_Item *m_glItem; + Evas_Object *m_progressBar; + Evas_Object *m_checkedBtn; + Eina_Bool m_checked; + bool m_isRetryCase; + int m_dateGroupType; +}; + +#endif /* DOWNLOAD_PROVIDER_VIEW_ITEM_H */ diff --git a/src/main.cpp b/src/main.cpp new file mode 100644 index 0000000..c3748b6 --- /dev/null +++ b/src/main.cpp @@ -0,0 +1,222 @@ +/* + * Copyright 2012 Samsung Electronics Co., Ltd + * + * Licensed under the Flora License, Version 1.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.tizenopensource.org/license + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/** + * @file main.cpp + * @author Jungki Kwak (jungki.kwak@samsung.com) + * @brief main file for download provider + */ + +#include +#include +#include +#include + +#include "Ecore_X.h" +#include "aul.h" +#include "vconf.h" +#include "app.h" +#include "app_service.h" + +#include "download-provider-common.h" +#include "download-provider-view.h" +#include "download-provider-network.h" +#include "download-provider-downloadRequest.h" +#include "download-provider-history-db.h" + +using namespace std; + +struct app_data_t { + Ecore_Idler *idler; + int history_count; + int load_count; +}; + +static void __lang_changed_cb(void *data) +{ + DP_LOG("=== Language changed nofification ==="); + return; +} + +static void __region_changed_cb(void *data) +{ + DownloadView &view = DownloadView::getInstance(); + view.changedRegion(); + DP_LOG("=== Region changed nofification ==="); + return; +} + +static void __low_memory_cb(void *data) +{ + DP_LOG("=== Low memory nofification ==="); + return; +} + +static Eina_Bool __load_remained_history(void *data) +{ + struct app_data_t *app_data = (struct app_data_t *)data; + if (app_data && app_data->load_count <= app_data->history_count) { + app_data->load_count += LOAD_HISTORY_COUNT; + DownloadHistoryDB::createRemainedItemsFromHistoryDB( + LOAD_HISTORY_COUNT, app_data->load_count); + return ECORE_CALLBACK_RENEW; + } else + return ECORE_CALLBACK_CANCEL; +} + +static bool __app_create(void *data) +{ + int count = 0; + struct app_data_t *app_data = (struct app_data_t *)data; + DP_LOG_START("App Create"); + + DownloadView &view = DownloadView::getInstance(); + Evas_Object *window = view.create(); + if (!window) { + DP_LOGE("Fail to create main window"); + return false; + } + /* Init network */ + NetMgr &netObj = NetMgr::getInstance(); + netObj.initNetwork(); + + evas_object_show(window); + view.show(); + + DownloadHistoryDB::getCountOfHistory(&count); + if (count > 0) { + DownloadHistoryDB::createItemsFromHistoryDB(); + if (count > LOAD_HISTORY_COUNT) { + if (app_data) { + app_data->history_count = count; + app_data->idler = ecore_idler_add(__load_remained_history, app_data); + } + } + } + + DP_LOG_END("App Create"); + + return true; +} + +static void __app_terminate(void *data) +{ + struct app_data_t *app_data = (struct app_data_t *)data; + NetMgr &netObj = NetMgr::getInstance(); + netObj.deinitNetwork(); + if (app_data && app_data->idler) + ecore_idler_del(app_data->idler); + if (app_data) { + free(app_data); + app_data = NULL; + } + return; +} + +static void __app_pause(void *data) +{ + DP_LOG_FUNC(); + return; +} + +static void __app_resume(void *data) +{ + return; +} + +static void __app_service(service_h s, void *data) +{ + string s_url = std::string(); + string s_cookie = std::string(); + char *url = NULL; + char *cookie = NULL; + char *mode = NULL; + char *app_op = NULL; + DownloadView &view = DownloadView::getInstance(); + + DP_LOG_FUNC(); + + if (service_get_operation(s, &app_op) < 0) { + DP_LOGE("Fail to get service operation"); + return; + } + DP_LOG("operation[%s]", app_op); + + if (service_get_uri(s, &url) < 0) { + DP_LOGE("Invalid URL"); + } else { + DP_LOG("url[%s]",url); + if (url) + s_url = url; + } + + if (service_get_extra_data(s, "cookie", &cookie) < 0) { + DP_LOG("No cookie"); + } else { + DP_LOG("cookie[%s]",cookie); + if (cookie) + s_cookie = cookie; + } + + if (service_get_extra_data(s, "mode", &mode) < 0) { + DP_LOG("No mode"); + } else { + DP_LOG("mode[%s]",mode); + if ( 0 == strncmp(mode, "view", strlen("view"))) { + DP_LOG("View mode"); + view.activateWindow(); + return; + } + DP_LOGE("Invalid mode"); + view.activateWindow(); + return; + } + + DownloadRequest request(s_url, s_cookie); + Item::create(request); + view.activateWindow(); + + return; +} + +int main(int argc, char *argv[]) +{ + app_event_callback_s evt_cb = {0,}; + int ret = 0; + struct app_data_t *app_data = NULL; + + app_data = (struct app_data_t *)calloc(1, sizeof(struct app_data_t)); + if (!app_data) { + DP_LOGE("Fail to calloc of app data"); + return ret; + } + + evt_cb.create = __app_create; + evt_cb.terminate = __app_terminate; + evt_cb.pause = __app_pause; + evt_cb.resume = __app_resume; + evt_cb.service = __app_service; + evt_cb.low_memory = __low_memory_cb; + evt_cb.low_battery = NULL; + evt_cb.device_orientation = NULL; + evt_cb.language_changed = __lang_changed_cb; + evt_cb.region_format_changed = __region_changed_cb; + + ret = app_efl_main(&argc, &argv, &evt_cb, app_data); + + return ret; +} +