Created
April 3, 2013 16:56
-
-
Save NikoYuwono/5303055 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<niko.twodimensionalscroll.PinchView xmlns:android="http://schemas.android.com/apk/res/android" | |
android:id="@+id/pvZoomContainer" | |
android:layout_width="wrap_content" | |
android:layout_height="wrap_content" > | |
<LinearLayout | |
android:id="@+id/llContainerMain" | |
android:layout_width="fill_parent" | |
android:layout_height="fill_parent" | |
android:orientation="vertical" > | |
<LinearLayout | |
android:id="@+id/llHeaderContainer" | |
android:layout_width="wrap_content" | |
android:layout_height="wrap_content" > | |
</LinearLayout> | |
<LinearLayout | |
android:layout_width="wrap_content" | |
android:layout_height="wrap_content" | |
android:orientation="horizontal" > | |
<LinearLayout | |
android:id="@+id/llLeftBarContainer" | |
android:layout_width="wrap_content" | |
android:layout_height="wrap_content" > | |
</LinearLayout> | |
<RelativeLayout | |
android:id="@+id/rlContainerScrollView" | |
android:layout_width="fill_parent" | |
android:layout_height="fill_parent" | |
android:drawingCacheQuality="low" > | |
<niko.twodimensionalscroll.TwoDScrollView | |
android:id="@+id/tdScrollView" | |
android:layout_width="fill_parent" | |
android:layout_height="fill_parent" | |
android:drawingCacheQuality="low" > | |
<LinearLayout | |
android:id="@+id/llContainerSchedule" | |
android:layout_width="wrap_content" | |
android:layout_height="wrap_content" | |
android:drawingCacheQuality="low" | |
android:orientation="horizontal" > | |
</LinearLayout> | |
</niko.twodimensionalscroll.TwoDScrollView> | |
</RelativeLayout> | |
</LinearLayout> | |
</LinearLayout> | |
</niko.twodimensionalscroll.PinchView> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package niko.twodimensionalscroll; | |
import android.content.Context; | |
import android.view.Gravity; | |
import android.view.View; | |
import android.widget.LinearLayout; | |
import android.widget.TextView; | |
import android.widget.Toast; | |
public class ChildDay extends LinearLayout { | |
private Context context; | |
private String programName; | |
private float programHour; | |
private ChildDay(Context context) { | |
super(context); | |
// TODO Auto-generated constructor stub | |
} | |
private ChildDay(Context context, String programName, int programHour, int type) { | |
super(context); | |
this.context = context; | |
this.programName = programName; | |
this.programHour = programHour; | |
LayoutParams lpChildDay = null; | |
if(type == BaseID.SCHEDULE_CONTENT) { | |
lpChildDay = new LayoutParams( | |
LayoutParams.FILL_PARENT, | |
(int) ((Util.getDisplayHeight(context) * 8) * (programHour / 1440.0))); | |
} else if(type == BaseID.SCHEDULE_LEFT_BAR) { | |
lpChildDay = new LayoutParams( | |
(int) Util.convertDipToPixels(context, 50), | |
(int) ((Util.getDisplayHeight(context) * 8) * (programHour / 1440.0))); | |
} | |
this.setLayoutParams(lpChildDay); | |
this.setBackgroundDrawable(context.getResources().getDrawable(R.drawable.border)); | |
this.setOrientation(VERTICAL); | |
final String test = programName; | |
final Context testContext = context; | |
this.setOnClickListener(new View.OnClickListener() { | |
@Override | |
public void onClick(View v) { | |
Toast.makeText(testContext, "TEST KELUAR : "+test, Toast.LENGTH_SHORT).show(); | |
} | |
}); | |
initView(); | |
} | |
public static ChildDay initChildDayProgramSchedule(Context context, String programName, int programHour, int type) { | |
ChildDay childDay = new ChildDay(context, programName, programHour, type); | |
return childDay; | |
} | |
public void initView() { | |
LinearLayout llContainerHour = new LinearLayout(context); | |
LayoutParams lpContainerHour = new LayoutParams(LayoutParams.FILL_PARENT, LayoutParams.WRAP_CONTENT); | |
lpContainerHour.gravity = Gravity.TOP; | |
llContainerHour.setLayoutParams(lpContainerHour); | |
llContainerHour.setGravity(Gravity.LEFT); | |
TextView tvHour = new TextView(context); | |
LayoutParams lpHour = new LayoutParams(LayoutParams.WRAP_CONTENT, | |
LayoutParams.WRAP_CONTENT); | |
tvHour.setLayoutParams(lpHour); | |
tvHour.setTextSize(14); | |
tvHour.setTextColor(context.getResources().getColor(R.color.black)); | |
tvHour.setText(Float.toString(programHour)); | |
llContainerHour.addView(tvHour); | |
TextView tvName = new TextView(context); | |
LayoutParams lpName = new LayoutParams(LayoutParams.WRAP_CONTENT, | |
LayoutParams.WRAP_CONTENT); | |
lpName.gravity = Gravity.CENTER; | |
tvName.setLayoutParams(lpName); | |
tvName.setTextSize(18); | |
tvName.setTextColor(context.getResources().getColor(R.color.black)); | |
tvName.setText(programName); | |
this.addView(llContainerHour); | |
this.addView(tvName); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package niko.twodimensionalscroll; | |
import java.util.ArrayList; | |
import android.content.Context; | |
import android.util.Log; | |
import android.widget.LinearLayout; | |
public class Day extends LinearLayout { | |
private Context context; | |
private TVProgramModel programModel; | |
private ArrayList<String> programName; | |
private ArrayList<Integer> programHour; | |
private Day(Context context) { | |
super(context); | |
this.context = context; | |
programModel = TVProgramModel.initTVProgramModelWithPrebuiltHour(); | |
LayoutParams lpDay = new LayoutParams((int) Util.convertDipToPixels(context, 50),LayoutParams.WRAP_CONTENT); | |
this.setLayoutParams(lpDay); | |
this.setOrientation(VERTICAL); | |
initContent(); | |
initView(BaseID.SCHEDULE_LEFT_BAR); | |
} | |
private Day(Context context, TVProgramModel programModel) { | |
super(context); | |
this.context = context; | |
this.programModel = programModel; | |
LayoutParams lpDay = new LayoutParams(Util.getDisplayWidth(context)/4,LayoutParams.WRAP_CONTENT); | |
this.setLayoutParams(lpDay); | |
this.setOrientation(VERTICAL); | |
initContent(); | |
initView(BaseID.SCHEDULE_CONTENT); | |
} | |
public static Day initDayScheduleHour(Context context) { | |
Day day = new Day(context); | |
return day; | |
} | |
public static Day initDayScheduleWithTVProgramModel(Context context, TVProgramModel programModel) { | |
Day day = new Day(context, programModel); | |
return day; | |
} | |
private void initContent() { | |
programName = programModel.getProgramName(); | |
programHour = programModel.getProgramHour(); | |
} | |
private void initView(int type) { | |
for(int i=0;i<programName.size();i++) { | |
this.addView(ChildDay.initChildDayProgramSchedule(context, programName.get(i), programHour.get(i), type)); | |
} | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package niko.twodimensionalscroll; | |
import java.util.ArrayList; | |
import niko.twodimensionalscroll.PinchView.PinchViewListener; | |
import android.os.Bundle; | |
import android.app.Activity; | |
import android.content.Context; | |
import android.view.MotionEvent; | |
import android.view.View; | |
import android.view.ViewGroup.LayoutParams; | |
import android.widget.LinearLayout; | |
import android.widget.RelativeLayout; | |
import android.widget.TextView; | |
public class MainActivity extends Activity { | |
private ArrayList<TVProgramModel> days; | |
private Context context; | |
private TwoDScrollView tdContainerSchedule, tdDate, tdLeftHour; | |
private LinearLayout llContainerSchedule, llContainerHorizontalHeader, | |
llGapFiller, llContainerChildHorizontalHeader, llDate, llLeft; | |
private PinchView pvContainerAll; | |
@Override | |
protected void onCreate(Bundle savedInstanceState) { | |
super.onCreate(savedInstanceState); | |
setContentView(R.layout.activity_main); | |
this.context = this; | |
days = new ArrayList<TVProgramModel>(); | |
initContent(); | |
initView(); | |
} | |
private void initContent() { | |
TVProgramModel mon = TVProgramModel.initTVProgramModel(); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("J-MELO", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("Itadakimasu!", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("ASIA 7 DAYS", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("TOMORROW beyond 3.11", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("J-MELO", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("ITADAKIMASU", 30); | |
mon.populateModel("ASIA 7 DAYS", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("TOMORROW beyond 3.11", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("J-MELO", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("ITADAKIMASU", 30); | |
mon.populateModel("ASIA 7 DAYS", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("TOMORROW beyond 3.11", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("J-MELO", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("Itadakimasu!", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("ASIA 7 DAYS", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("TOMORROW beyond 3.11", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("J-MELO", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("ITADAKIMASU", 30); | |
mon.populateModel("ASIA 7 DAYS", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("TOMORROW beyond 3.11", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("J-MELO", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("ITADAKIMASU", 30); | |
mon.populateModel("ASIA 7 DAYS", 30); | |
mon.populateModel("NEWSLINE", 30); | |
mon.populateModel("TOMORROW beyond 3.11", 30); | |
days.add(mon); | |
TVProgramModel tue = TVProgramModel.initTVProgramModel(); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("TOKYO FASHION EXPRESS", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("journeys in japan", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("Today's Close-Up", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("At Home with Venetia in Kyoto", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("TOKYO FASHION EXPRESS", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("journeys in japan", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("Today's Close-Up", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("At Home with Venetia in Kyoto", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("TOKYO FASHION EXPRESS", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("journeys in japan", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("Today's Close-Up", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("At Home with Venetia in Kyoto", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("TOKYO FASHION EXPRESS", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("journeys in japan", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("Today's Close-Up", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("At Home with Venetia in Kyoto", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("TOKYO FASHION EXPRESS", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("journeys in japan", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("Today's Close-Up", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("At Home with Venetia in Kyoto", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("TOKYO FASHION EXPRESS", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("journeys in japan", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("Today's Close-Up", 30); | |
tue.populateModel("NEWSLINE", 30); | |
tue.populateModel("At Home with Venetia in Kyoto", 30); | |
days.add(tue); | |
TVProgramModel wed = TVProgramModel.initTVProgramModel(); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("imagine-nation", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("TOKYO EYE", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("Today's Close-Up", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("MAPPING KYOTO STREETS", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("imagine-nation", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("TOKYO EYE", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("Today's Close-Up", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("MAPPING KYOTO STREETS", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("imagine-nation", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("TOKYO EYE", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("Today's Close-Up", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("MAPPING KYOTO STREETS", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("imagine-nation", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("TOKYO EYE", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("Today's Close-Up", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("MAPPING KYOTO STREETS", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("imagine-nation", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("TOKYO EYE", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("Today's Close-Up", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("MAPPING KYOTO STREETS", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("imagine-nation", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("TOKYO EYE", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("Today's Close-Up", 30); | |
wed.populateModel("NEWSLINE", 30); | |
wed.populateModel("MAPPING KYOTO STREETS", 30); | |
days.add(wed); | |
TVProgramModel thu = TVProgramModel.initTVProgramModel(); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("Great Gear", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("Begin Japanology", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("WORLD TV TRYOUT", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("TAKESHI Art Beat", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("Great Gear", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("Begin Japanology", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("WORLD TV TRYOUT", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("TAKESHI Art Beat", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("Great Gear", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("Begin Japanology", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("WORLD TV TRYOUT", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("TAKESHI Art Beat", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("Great Gear", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("Begin Japanology", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("WORLD TV TRYOUT", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("TAKESHI Art Beat", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("Great Gear", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("Begin Japanology", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("WORLD TV TRYOUT", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("TAKESHI Art Beat", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("Great Gear", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("Begin Japanology", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("WORLD TV TRYOUT", 30); | |
thu.populateModel("NEWSLINE", 30); | |
thu.populateModel("TAKESHI Art Beat", 30); | |
days.add(thu); | |
TVProgramModel fri = TVProgramModel.initTVProgramModel(); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("Science View", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("JIB Program", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("ASIAN VOICES", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("Asia Insight", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("Science View", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("JIB Program", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("ASIAN VOICES", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("Asia Insight", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("Science View", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("JIB Program", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("ASIAN VOICES", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("Asia Insight", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("Science View", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("JIB Program", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("ASIAN VOICES", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("Asia Insight", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("Science View", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("JIB Program", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("ASIAN VOICES", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("Asia Insight", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("Science View", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("JIB Program", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("ASIAN VOICES", 30); | |
fri.populateModel("NEWSLINE", 30); | |
fri.populateModel("Asia Insight", 30); | |
days.add(fri); | |
TVProgramModel sat = TVProgramModel.initTVProgramModel(); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("Kawaii International", 45); | |
sat.populateModel("YJK mini", 5); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("WORLD TV SELECTION", 50); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("Festivals of the Orient!", 10); | |
sat.populateModel("Four Seasons in Japan", 10); | |
sat.populateModel("JAPAN 7 DAYS", 30); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("NHK Documentary", 45); | |
sat.populateModel("YJK mini", 5); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("Kawaii International", 45); | |
sat.populateModel("YJK mini", 5); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("WORLD TV SELECTION", 50); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("Festivals of the Orient!", 10); | |
sat.populateModel("Four Seasons in Japan", 10); | |
sat.populateModel("JAPAN 7 DAYS", 30); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("NHK Documentary", 45); | |
sat.populateModel("YJK mini", 5); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("Kawaii International", 45); | |
sat.populateModel("YJK mini", 5); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("WORLD TV SELECTION", 50); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("Festivals of the Orient!", 10); | |
sat.populateModel("Four Seasons in Japan", 10); | |
sat.populateModel("JAPAN 7 DAYS", 30); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("NHK Documentary", 45); | |
sat.populateModel("YJK mini", 5); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("Kawaii International", 45); | |
sat.populateModel("YJK mini", 5); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("WORLD TV SELECTION", 50); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("Festivals of the Orient!", 10); | |
sat.populateModel("Four Seasons in Japan", 10); | |
sat.populateModel("JAPAN 7 DAYS", 30); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("NHK Documentary", 45); | |
sat.populateModel("YJK mini", 5); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("Kawaii International", 45); | |
sat.populateModel("YJK mini", 5); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("WORLD TV SELECTION", 50); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("Festivals of the Orient!", 10); | |
sat.populateModel("Four Seasons in Japan", 10); | |
sat.populateModel("JAPAN 7 DAYS", 30); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("NHK Documentary", 45); | |
sat.populateModel("YJK mini", 5); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("Kawaii International", 45); | |
sat.populateModel("YJK mini", 5); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("WORLD TV SELECTION", 50); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("Festivals of the Orient!", 10); | |
sat.populateModel("Four Seasons in Japan", 10); | |
sat.populateModel("JAPAN 7 DAYS", 30); | |
sat.populateModel("NEWSLINE", 10); | |
sat.populateModel("NHK Documentary", 45); | |
sat.populateModel("YJK mini", 5); | |
days.add(sat); | |
TVProgramModel sun = TVProgramModel.initTVProgramModel(); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("cool japan", 45); | |
sun.populateModel("Fudoki", 5); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("SPORTS JAPAN", 30); | |
sun.populateModel("Meet and Speak", 10); | |
sun.populateModel("Satoyama", 10); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("March to Recovery", 50); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("ASIA BIZ FORECAST", 30); | |
sun.populateModel("Inspiring Landscapes", 15); | |
sun.populateModel("NHK Documentary 5 min", 5); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("cool japan", 45); | |
sun.populateModel("Fudoki", 5); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("SPORTS JAPAN", 30); | |
sun.populateModel("Meet and Speak", 10); | |
sun.populateModel("Satoyama", 10); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("March to Recovery", 50); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("ASIA BIZ FORECAST", 30); | |
sun.populateModel("Inspiring Landscapes", 15); | |
sun.populateModel("NHK Documentary 5 min", 5); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("cool japan", 45); | |
sun.populateModel("Fudoki", 5); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("SPORTS JAPAN", 30); | |
sun.populateModel("Meet and Speak", 10); | |
sun.populateModel("Satoyama", 10); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("March to Recovery", 50); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("ASIA BIZ FORECAST", 30); | |
sun.populateModel("Inspiring Landscapes", 15); | |
sun.populateModel("NHK Documentary 5 min", 5); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("cool japan", 45); | |
sun.populateModel("Fudoki", 5); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("SPORTS JAPAN", 30); | |
sun.populateModel("Meet and Speak", 10); | |
sun.populateModel("Satoyama", 10); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("March to Recovery", 50); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("ASIA BIZ FORECAST", 30); | |
sun.populateModel("Inspiring Landscapes", 15); | |
sun.populateModel("NHK Documentary 5 min", 5); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("cool japan", 45); | |
sun.populateModel("Fudoki", 5); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("SPORTS JAPAN", 30); | |
sun.populateModel("Meet and Speak", 10); | |
sun.populateModel("Satoyama", 10); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("March to Recovery", 50); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("ASIA BIZ FORECAST", 30); | |
sun.populateModel("Inspiring Landscapes", 15); | |
sun.populateModel("NHK Documentary 5 min", 5); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("cool japan", 45); | |
sun.populateModel("Fudoki", 5); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("SPORTS JAPAN", 30); | |
sun.populateModel("Meet and Speak", 10); | |
sun.populateModel("Satoyama", 10); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("March to Recovery", 50); | |
sun.populateModel("NEWSLINE", 10); | |
sun.populateModel("ASIA BIZ FORECAST", 30); | |
sun.populateModel("Inspiring Landscapes", 15); | |
sun.populateModel("NHK Documentary 5 min", 5); | |
days.add(sun); | |
} | |
private void initView() { | |
pvContainerAll = (PinchView) findViewById(R.id.pvZoomContainer); | |
pvContainerAll.setPinchViewListener(new pinchViewListener()); | |
tdContainerSchedule = (TwoDScrollView) findViewById(R.id.tdScrollView); | |
RelativeLayout.LayoutParams lpSceneLayout = new RelativeLayout.LayoutParams( | |
LayoutParams.FILL_PARENT, LayoutParams.FILL_PARENT); | |
tdContainerSchedule.setLayoutParams(lpSceneLayout); | |
tdContainerSchedule.setScrollViewListener(new diagonalScrollSync()); | |
llContainerSchedule = (LinearLayout) findViewById(R.id.llContainerSchedule); | |
for (int i = 0; i < days.size(); i++) { | |
llContainerSchedule.addView(Day.initDayScheduleWithTVProgramModel( | |
context, days.get(i))); | |
} | |
LinearLayout llHeader = createHorizontalHeader(); | |
tdLeftHour = createLeftHourScroll(); | |
tdLeftHour.setOnTouchListener(new View.OnTouchListener() { | |
@Override | |
public boolean onTouch(View v, MotionEvent event) { | |
return true; | |
} | |
}); | |
LinearLayout llHeaderContainer = (LinearLayout) findViewById(R.id.llHeaderContainer); | |
LinearLayout llLeftBarContainer = (LinearLayout) findViewById(R.id.llLeftBarContainer); | |
llHeaderContainer.addView(llHeader); | |
llLeftBarContainer.addView(tdLeftHour); | |
} | |
private TwoDScrollView createLeftHourScroll() { | |
llLeft = Day.initDayScheduleHour(context); | |
TwoDScrollView svLeftHour = new TwoDScrollView(context); | |
svLeftHour.setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT, | |
LayoutParams.WRAP_CONTENT)); | |
svLeftHour.setScrollViewListener(new diagonalScrollSync()); | |
svLeftHour.addView(llLeft); | |
return svLeftHour; | |
} | |
private LinearLayout createHorizontalHeader() { | |
llContainerHorizontalHeader = new LinearLayout(context); | |
LayoutParams lpContainerHorizontalHeader = new LayoutParams( | |
LayoutParams.FILL_PARENT, LayoutParams.WRAP_CONTENT); | |
llContainerHorizontalHeader | |
.setLayoutParams(lpContainerHorizontalHeader); | |
llContainerHorizontalHeader.setOrientation(LinearLayout.HORIZONTAL); | |
llGapFiller = new LinearLayout(context); | |
LayoutParams lpGapFiller = new LayoutParams( | |
(int) Util.convertDipToPixels(context, 50), | |
(int) ((Util.getDisplayHeight(context) * 8) * (20 / 1440.0))); | |
llGapFiller.setLayoutParams(lpGapFiller); | |
llGapFiller.setBackgroundDrawable(context.getResources().getDrawable( | |
R.drawable.border)); | |
tdDate = new TwoDScrollView(context); | |
LayoutParams lpHsvDate = new LayoutParams(LayoutParams.WRAP_CONTENT, | |
LayoutParams.WRAP_CONTENT); | |
tdDate.setLayoutParams(lpHsvDate); | |
tdDate.setHorizontalScrollBarEnabled(false); | |
tdDate.setHorizontalFadingEdgeEnabled(false); | |
tdDate.setScrollViewListener(new diagonalScrollSync()); | |
tdDate.setOnTouchListener(new View.OnTouchListener() { | |
@Override | |
public boolean onTouch(View v, MotionEvent event) { | |
return true; | |
} | |
}); | |
llContainerChildHorizontalHeader = new LinearLayout(context); | |
LayoutParams lpContainerChildHorizontalHeader = new LayoutParams( | |
LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT); | |
llContainerChildHorizontalHeader | |
.setOrientation(LinearLayout.HORIZONTAL); | |
llContainerChildHorizontalHeader | |
.setLayoutParams(lpContainerChildHorizontalHeader); | |
for (int i = 0; i < 7; i++) { | |
llContainerChildHorizontalHeader | |
.addView(createChildHorizontalHeader("testday", | |
"testmonth", "testdayname")); | |
} | |
tdDate.addView(llContainerChildHorizontalHeader); | |
llContainerHorizontalHeader.addView(llGapFiller); | |
llContainerHorizontalHeader.addView(tdDate); | |
return llContainerHorizontalHeader; | |
} | |
private LinearLayout createChildHorizontalHeader(String day, String month, | |
String dayName) { | |
llDate = new LinearLayout(context); | |
LayoutParams lpDate = new LayoutParams( | |
Util.getDisplayWidth(context) / 4, | |
(int) ((Util.getDisplayHeight(context) * 8) * (20 / 1440.0))); | |
llDate.setLayoutParams(lpDate); | |
llDate.setBackgroundDrawable(context.getResources().getDrawable( | |
R.drawable.border)); | |
TextView tvDay = new TextView(context); | |
LayoutParams lpDay = new LayoutParams(LayoutParams.WRAP_CONTENT, | |
LayoutParams.WRAP_CONTENT); | |
tvDay.setLayoutParams(lpDay); | |
tvDay.setText(day); | |
TextView tvMonth = new TextView(context); | |
LayoutParams lpMonth = new LayoutParams(LayoutParams.WRAP_CONTENT, | |
LayoutParams.WRAP_CONTENT); | |
tvMonth.setLayoutParams(lpMonth); | |
tvMonth.setText(month); | |
TextView tvDayName = new TextView(context); | |
LayoutParams lpDayName = new LayoutParams(LayoutParams.WRAP_CONTENT, | |
LayoutParams.WRAP_CONTENT); | |
tvDayName.setLayoutParams(lpDayName); | |
tvDayName.setText(dayName); | |
llDate.addView(tvDay); | |
llDate.addView(tvMonth); | |
llDate.addView(tvDayName); | |
return llDate; | |
} | |
private class diagonalScrollSync implements SyncTwoDScrollListener { | |
@Override | |
public void onScrollChanged(TwoDScrollView scrollView, int x, int y, | |
int oldx, int oldy) { | |
if (scrollView == tdContainerSchedule) { | |
tdLeftHour.scrollTo(x, y); | |
tdDate.scrollTo(x, y); | |
} | |
} | |
} | |
@Override | |
public void onWindowFocusChanged(boolean hasFocus) { | |
super.onWindowFocusChanged(hasFocus); | |
} | |
private class pinchViewListener implements PinchViewListener { | |
@Override | |
public void onZoom(float scale) { | |
zoomHeaderWithScale(scale); | |
zoomLeftBarWithScale(scale); | |
zoomContentWithScale(scale); | |
} | |
} | |
private void zoomHeaderWithScale(float scale) { | |
float newGapWidth = llGapFiller.getWidth() * scale; | |
float newGapHeight = llGapFiller.getHeight() * scale; | |
if ((newGapHeight > (int) ((Util.getDisplayHeight(context) * 8) * (20 / 1440.0))) | |
&& (newGapHeight < (int) ((Util.getDisplayHeight(context) * 12) * (20 / 1440.0)))) { | |
llGapFiller.setLayoutParams(new LinearLayout.LayoutParams( | |
(int) newGapWidth, (int) newGapHeight)); | |
} | |
for (int i = 0; i < llContainerChildHorizontalHeader.getChildCount(); i++) { | |
View child = llContainerChildHorizontalHeader.getChildAt(i); | |
float newWidth = child.getWidth() * scale; | |
float newHeight = child.getHeight() * scale; | |
if ((newHeight > (int) ((Util.getDisplayHeight(context) * 8) * (20 / 1440.0))) | |
&& (newHeight < (int) ((Util.getDisplayHeight(context) * 12) * (20 / 1440.0)))) { | |
child.setLayoutParams(new LinearLayout.LayoutParams( | |
(int) newWidth, (int) newHeight)); | |
} | |
} | |
} | |
private void zoomLeftBarWithScale(float scale) { | |
for (int i = 0; i < llLeft.getChildCount(); i++) { | |
View child = llLeft.getChildAt(i); | |
float newWidth = child.getWidth() * scale; | |
float newHeight = child.getHeight() * scale; | |
if (isValidLeftBarSize(newWidth, newHeight)) { | |
child.setLayoutParams(new LinearLayout.LayoutParams( | |
(int) newWidth, (int) newHeight)); | |
} | |
} | |
} | |
private void zoomContentWithScale(float scale) { | |
for (int i = 0; i < llContainerSchedule.getChildCount(); i++) { | |
View childView = llContainerSchedule.getChildAt(i); | |
if(childView instanceof LinearLayout) { | |
LinearLayout llChild = (LinearLayout) childView; | |
float newChildWidth = llChild.getWidth() * scale; | |
float newChildHeight = llChild.getHeight() * scale; | |
for (int j = 0; j < llChild.getChildCount(); j++) { | |
View grandChildView = llChild.getChildAt(i); | |
float newGrandChildWidth = grandChildView.getWidth() * scale; | |
float newGrandChildHeight = grandChildView.getHeight() * scale; | |
if ((newGrandChildWidth > Util.getDisplayWidth(context)/4) | |
&& (newGrandChildWidth < Util.getDisplayWidth(context)/2)) { | |
grandChildView.setLayoutParams(new LinearLayout.LayoutParams( | |
(int) newGrandChildWidth, (int) newGrandChildHeight)); | |
childView.setLayoutParams(new LinearLayout.LayoutParams( | |
(int) newChildWidth, (int) newChildHeight)); | |
} | |
} | |
} | |
} | |
} | |
private boolean isValidLeftBarSize(float newWidth, float newHeight) { | |
return (newHeight > (int) ((Util.getDisplayHeight(context) * 8) * (60 / 1440.0))) | |
&& (newHeight < (int) ((Util.getDisplayHeight(context) * 12) * (60 / 1440.0))); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package niko.twodimensionalscroll; | |
import android.content.Context; | |
import android.util.AttributeSet; | |
import android.util.FloatMath; | |
import android.util.Log; | |
import android.view.MotionEvent; | |
import android.widget.LinearLayout; | |
public class PinchView extends LinearLayout { | |
private final int MODE_ZOOMING = 0; | |
private final int MODE_NOT_ZOOMING = 1; | |
private PinchViewListener pvListener; | |
private float oldDist = 0; | |
private int mode = MODE_NOT_ZOOMING; | |
public interface PinchViewListener { | |
void onZoom(float scale); | |
} | |
public PinchView(Context context) { | |
super(context); | |
} | |
public PinchView(Context context, AttributeSet attrs) { | |
super(context, attrs); | |
} | |
@Override | |
public boolean onInterceptTouchEvent(MotionEvent ev) { | |
onTouchEvent(ev); | |
return false; | |
} | |
public void setPinchViewListener(PinchViewListener pvListener) { | |
this.pvListener = pvListener; | |
} | |
@Override | |
public boolean onTouchEvent(MotionEvent ev) { | |
final int action = ev.getActionMasked(); | |
switch (action) { | |
case MotionEvent.ACTION_POINTER_DOWN: { | |
oldDist = spacing(ev); | |
Log.d("TAG", "oldDist=" + oldDist); | |
if (oldDist > 5f) { | |
mode = MODE_ZOOMING; | |
} | |
} | |
case MotionEvent.ACTION_MOVE: { | |
if(mode == MODE_ZOOMING) { | |
float newDist = spacing(ev); | |
if (newDist > 5f) { | |
float scale = newDist / oldDist; | |
if(scale < 0.5f) { | |
scale = 0.5f; | |
} else if (scale > 2.0f) { | |
scale = 2.0f; | |
} | |
if(pvListener!=null) { | |
pvListener.onZoom(scale); | |
} | |
} | |
} | |
break; | |
} | |
case MotionEvent.ACTION_UP: { | |
mode = MODE_NOT_ZOOMING; | |
break; | |
} | |
case MotionEvent.ACTION_CANCEL: { | |
mode = MODE_NOT_ZOOMING; | |
break; | |
} | |
case MotionEvent.ACTION_POINTER_UP: { | |
mode = MODE_NOT_ZOOMING; | |
break; | |
} | |
} | |
return true; | |
} | |
private float spacing(MotionEvent event) { | |
float x = event.getX(0) - event.getX(1); | |
float y = event.getY(0) - event.getY(1); | |
return FloatMath.sqrt(x * x + y * y); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment