new plotter

This commit is contained in:
Sergey Solovyev 2013-01-13 21:17:11 +04:00
parent 3f09528f45
commit 76719407db
25 changed files with 409 additions and 172 deletions

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 891 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 698 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.3 KiB

View File

@ -0,0 +1,26 @@
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:a="http://schemas.android.com/apk/res/android"
a:layout_width="match_parent"
a:layout_height="wrap_content"
a:orientation="horizontal">
<TextView
a:id="@+id/cpp_plot_function_expression_textview"
a:layout_width="0dp"
a:layout_height="wrap_content"
a:layout_weight="5"/>
<CheckBox
a:id="@+id/cpp_plot_function_pinned_checkbox"
a:layout_width="0dp"
a:layout_height="wrap_content"
a:layout_weight="1"/>
<CheckBox
a:id="@+id/cpp_plot_function_visible_checkbox"
a:layout_width="0dp"
a:layout_height="wrap_content"
a:layout_weight="1"/>
</LinearLayout>

View File

@ -1,5 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:a="http://schemas.android.com/apk/res/android"
a:layout_width="match_parent"
a:layout_height="wrap_content"/>

View File

@ -282,7 +282,9 @@
<string name="cpp_onscreen_remove_icon_message">You can remove second icon in applications\' list from application settings or by pressing next button</string> <string name="cpp_onscreen_remove_icon_message">You can remove second icon in applications\' list from application settings or by pressing next button</string>
<string name="cpp_onscreen_remove_icon_button_text">Remove icon</string> <string name="cpp_onscreen_remove_icon_button_text">Remove icon</string>
<string name="cpp_this_change_may_require_reboot">This change may require reboot</string> <string name="cpp_this_change_may_require_reboot">This change may require reboot</string>
<string name="cpp_plot_3d">3D</string> <string name="cpp_plot_2d">2D plot</string>
<string name="cpp_plot_3d">3D plot</string>
<string name="cpp_plot_functions">Graph functions</string>
<string name="cpp_prefs_graph_plot_imag_title">Plot imaginary part of function</string> <string name="cpp_prefs_graph_plot_imag_title">Plot imaginary part of function</string>
<string name="cpp_prefs_graph_plot_imag_summary">If checked imaginary part of function will be plotted</string> <string name="cpp_prefs_graph_plot_imag_summary">If checked imaginary part of function will be plotted</string>

View File

@ -152,7 +152,30 @@
<item name="dropDownListViewStyle">@style/cpp_default_actionbar_dropdown_listview_style</item> <item name="dropDownListViewStyle">@style/cpp_default_actionbar_dropdown_listview_style</item>
<item name="android:dropDownListViewStyle">@style/cpp_default_actionbar_dropdown_listview_style</item> <item name="android:dropDownListViewStyle">@style/cpp_default_actionbar_dropdown_listview_style</item>
</style> </style>
<style name="cpp_gray_dialog_theme" parent="Theme.Sherlock.Dialog">
<!-- buttons -->
<item name="cpp_digit_button_style">@style/cpp_default_digit_button_style</item>
<item name="cpp_control_button_style">@style/cpp_default_control_button_style</item>
<item name="cpp_control_image_button_style">@style/cpp_default_control_image_button_style</item>
<item name="cpp_operation_button_style">@style/cpp_default_operation_button_style</item>
<!-- other -->
<item name="cpp_fragment_title_style">@style/cpp_default_fragment_title_style</item>
<item name="cpp_fragment_list_view_style">@style/cpp_default_fragment_list_view_style</item>
<item name="cpp_fragment_list_view_item_style">@style/cpp_default_fragment_list_view_item_style</item>
<item name="cpp_button_style">@style/cpp_default_button_style</item>
<item name="cpp_main_layout_style">@style/cpp_default_main_layout_style</item>
<item name="cpp_main_multi_pane_layout_style">@style/cpp_default_main_multi_pane_layout_style</item>
<item name="cpp_fragment_layout_style">@style/cpp_default_fragment_layout_style</item>
<item name="cpp_dialog_style">@style/cpp_default_dialog_style</item>
<item name="cpp_pane_style">@style/cpp_default_pane_style</item>
<item name="cpp_pane_style_transparent">@style/cpp_default_pane_style_transparent</item>
</style>
</resources> </resources>

View File

@ -86,7 +86,7 @@ public enum CalculatorDisplayMenuItem implements LabeledMenuItem<CalculatorDispl
@Override @Override
protected boolean isItemVisibleFor(@NotNull Generic generic, @NotNull JsclOperation operation) { protected boolean isItemVisibleFor(@NotNull Generic generic, @NotNull JsclOperation operation) {
return Locator.getInstance().getPlotter().isPlotPossible(generic); return Locator.getInstance().getPlotter().isPlotPossibleFor(generic);
} }
}; };

View File

@ -77,24 +77,28 @@ public class AndroidCalculatorPlotter implements CalculatorPlotter, SharedPrefer
return plotter.removeFunction(xyFunction); return plotter.removeFunction(xyFunction);
} }
@NotNull
@Override @Override
public void pin(@NotNull PlotFunction plotFunction) { public PlotFunction pin(@NotNull PlotFunction plotFunction) {
plotter.pin(plotFunction); return plotter.pin(plotFunction);
} }
@NotNull
@Override @Override
public void unpin(@NotNull PlotFunction plotFunction) { public PlotFunction unpin(@NotNull PlotFunction plotFunction) {
plotter.unpin(plotFunction); return plotter.unpin(plotFunction);
} }
@NotNull
@Override @Override
public void show(@NotNull PlotFunction plotFunction) { public PlotFunction show(@NotNull PlotFunction plotFunction) {
plotter.show(plotFunction); return plotter.show(plotFunction);
} }
@NotNull
@Override @Override
public void hide(@NotNull PlotFunction plotFunction) { public PlotFunction hide(@NotNull PlotFunction plotFunction) {
plotter.hide(plotFunction); return plotter.hide(plotFunction);
} }
@Override @Override
@ -120,8 +124,13 @@ public class AndroidCalculatorPlotter implements CalculatorPlotter, SharedPrefer
} }
@Override @Override
public boolean isPlotPossible(@NotNull Generic expression) { public boolean is2dPlotPossible() {
return plotter.isPlotPossible(expression); return plotter.is2dPlotPossible();
}
@Override
public boolean isPlotPossibleFor(@NotNull Generic expression) {
return plotter.isPlotPossibleFor(expression);
} }
@Override @Override

View File

@ -1,57 +0,0 @@
package org.solovyev.android.calculator.plot;
import android.content.Context;
import android.view.View;
import android.widget.TextView;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.solovyev.android.calculator.core.R;
import org.solovyev.android.list.ListItem;
import org.solovyev.android.view.TextViewBuilder;
import org.solovyev.android.view.UpdatableViewBuilder;
public class ParcelablePlotInputListItem implements ListItem {
@NotNull
private XyFunction plotInput;
@NotNull
private UpdatableViewBuilder<TextView> viewBuilder;
public ParcelablePlotInputListItem(@NotNull XyFunction plotInput) {
this.plotInput = plotInput;
// todo serso: use correct tag
this.viewBuilder = TextViewBuilder.newInstance(R.layout.plot_functions_fragment_list_item, null);
}
@Nullable
@Override
public OnClickAction getOnClickAction() {
return null;
}
@Nullable
@Override
public OnClickAction getOnLongClickAction() {
return null;
}
@NotNull
@Override
public View updateView(@NotNull Context context, @NotNull View view) {
// todo serso: optimize
return build(context);
}
@NotNull
@Override
public View build(@NotNull Context context) {
TextView textView = viewBuilder.build(context);
fill(textView);
return textView;
}
private void fill(@NotNull TextView textView) {
textView.setText(plotInput.getExpressionString());
}
}

View File

@ -0,0 +1,119 @@
package org.solovyev.android.calculator.plot;
import android.content.Context;
import android.view.View;
import android.widget.CheckBox;
import android.widget.CompoundButton;
import android.widget.TextView;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.solovyev.android.calculator.Locator;
import org.solovyev.android.calculator.core.R;
import org.solovyev.android.list.ListItem;
import org.solovyev.android.view.ViewBuilder;
import org.solovyev.android.view.ViewFromLayoutBuilder;
public class PlotFunctionListItem implements ListItem {
private static final String PREFIX = "plot_function_";
@NotNull
private PlotFunction plotFunction;
@NotNull
private ViewBuilder<View> viewBuilder;
@NotNull
private String tag;
public PlotFunctionListItem(@NotNull PlotFunction plotFunction) {
this.plotFunction = plotFunction;
this.viewBuilder = ViewFromLayoutBuilder.newInstance(R.layout.cpp_plot_function_list_item);
this.tag = PREFIX + plotFunction.getXyFunction().getExpressionString();
}
@Nullable
@Override
public OnClickAction getOnClickAction() {
return null;
}
@Nullable
@Override
public OnClickAction getOnLongClickAction() {
return null;
}
@NotNull
@Override
public View updateView(@NotNull Context context, @NotNull View view) {
final Object viewTag = view.getTag();
if ( viewTag instanceof String ) {
if ( this.tag.equals(viewTag) ) {
return view;
} else if (((String) viewTag).startsWith(PREFIX)) {
fillView(view);
return view;
} else {
return build(context);
}
}
return build(context);
}
@NotNull
@Override
public View build(@NotNull Context context) {
final View root = buildView(context);
fillView(root);
return root;
}
private View buildView(@NotNull Context context) {
return viewBuilder.build(context);
}
private void fillView(@NotNull View root) {
root.setTag(tag);
final CalculatorPlotter plotter = Locator.getInstance().getPlotter();
final TextView expressionTextView = (TextView) root.findViewById(R.id.cpp_plot_function_expression_textview);
expressionTextView.setText(plotFunction.getXyFunction().getExpressionString());
final CheckBox pinnedCheckBox = (CheckBox) root.findViewById(R.id.cpp_plot_function_pinned_checkbox);
pinnedCheckBox.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean pin) {
if (pin) {
if (!plotFunction.isPinned()) {
plotFunction = plotter.pin(plotFunction);
}
} else {
if (plotFunction.isPinned()) {
plotFunction = plotter.unpin(plotFunction);
}
}
}
});
pinnedCheckBox.setChecked(plotFunction.isPinned());
final CheckBox visibleCheckBox = (CheckBox) root.findViewById(R.id.cpp_plot_function_visible_checkbox);
visibleCheckBox.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean show) {
if (show) {
if (!plotFunction.isVisible()) {
plotFunction = plotter.show(plotFunction);
}
} else {
if (plotFunction.isVisible()) {
plotFunction = plotter.hide(plotFunction);
}
}
}
});
visibleCheckBox.setChecked(plotFunction.isVisible());
}
}

View File

@ -52,6 +52,7 @@
<activity android:label="@string/c_vars_and_constants" android:name=".math.edit.CalculatorVarsActivity"/> <activity android:label="@string/c_vars_and_constants" android:name=".math.edit.CalculatorVarsActivity"/>
<activity android:label="@string/c_plot_graph" android:name=".plot.CalculatorPlotActivity"/> <activity android:label="@string/c_plot_graph" android:name=".plot.CalculatorPlotActivity"/>
<activity android:label="@string/c_plot_graph" android:name=".plot.CalculatorPlotFunctionsActivity" android:theme="@style/cpp_gray_dialog_theme"/>
<!-- todo serso: strings--> <!-- todo serso: strings-->
<activity android:label="@string/c_plot_graph" android:name=".matrix.CalculatorMatrixActivity"/> <activity android:label="@string/c_plot_graph" android:name=".matrix.CalculatorMatrixActivity"/>

View File

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:a="http://schemas.android.com/apk/res/android"
a:layout_width="wrap_content"
a:layout_height="wrap_content"
a:id="@+id/dialog_layout"
style="?cpp_dialog_style"
a:orientation="vertical">
</LinearLayout>

View File

@ -6,13 +6,40 @@
a:layout_width="match_parent" a:layout_width="match_parent"
a:layout_height="match_parent"> a:layout_height="match_parent">
<TextView a:id="@+id/fragment_title" <TextView
a:id="@+id/fragment_title"
a:layout_height="wrap_content" a:layout_height="wrap_content"
a:layout_width="match_parent" a:layout_width="match_parent"
style="?cpp_fragment_title_style" /> style="?cpp_fragment_title_style" />
<include layout="@layout/ad" /> <include layout="@layout/ad" />
<LinearLayout
a:layout_width="match_parent"
a:layout_height="wrap_content"
a:orientation="horizontal">
<TextView
a:layout_width="0dp"
a:layout_height="wrap_content"
a:layout_weight="5"
a:text="Function"/>
<TextView
a:layout_width="0dp"
a:layout_height="wrap_content"
a:layout_weight="1"
a:text="Pinned"/>
<TextView
a:layout_width="0dp"
a:layout_height="wrap_content"
a:layout_weight="1"
a:text="Visible"/>
</LinearLayout>
<ListView style="?cpp_fragment_list_view_style" /> <ListView style="?cpp_fragment_list_view_style" />
</LinearLayout> </LinearLayout>

View File

@ -8,9 +8,19 @@
<menu xmlns:a="http://schemas.android.com/apk/res/android"> <menu xmlns:a="http://schemas.android.com/apk/res/android">
<item a:id="@+id/menu_plot_2d"
a:title="@string/cpp_plot_2d"
a:icon="@drawable/ab_plot_2d"
a:showAsAction="always"/>
<item a:id="@+id/menu_plot_3d" <item a:id="@+id/menu_plot_3d"
a:title="@string/cpp_plot_3d" a:title="@string/cpp_plot_3d"
a:icon="@drawable/ab_icon" a:icon="@drawable/ab_plot_3d"
a:showAsAction="always"/>
<item a:id="@+id/menu_plot_functions"
a:title="@string/cpp_plot_functions"
a:icon="@drawable/ab_list"
a:showAsAction="always"/> a:showAsAction="always"/>
<item a:id="@+id/menu_plot_settings" <item a:id="@+id/menu_plot_settings"

View File

@ -14,10 +14,12 @@ import org.achartengine.renderer.XYMultipleSeriesRenderer;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable; import org.jetbrains.annotations.Nullable;
import org.solovyev.android.calculator.*; import org.solovyev.android.calculator.*;
import org.solovyev.android.menu.AMenuItem;
import org.solovyev.android.menu.ActivityMenu; import org.solovyev.android.menu.ActivityMenu;
import org.solovyev.android.menu.IdentifiableMenuItem; import org.solovyev.android.menu.IdentifiableMenuItem;
import org.solovyev.android.menu.ListActivityMenu; import org.solovyev.android.menu.ListActivityMenu;
import org.solovyev.android.sherlock.menu.SherlockMenuHelper; import org.solovyev.android.sherlock.menu.SherlockMenuHelper;
import org.solovyev.common.JPredicate;
import java.io.Serializable; import java.io.Serializable;
import java.util.ArrayList; import java.util.ArrayList;
@ -97,13 +99,6 @@ public abstract class AbstractCalculatorPlotFragment extends CalculatorFragment
setHasOptionsMenu(true); setHasOptionsMenu(true);
} }
@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
this.plotData = Locator.getInstance().getPlotter().getPlotData();
}
@Override @Override
public void onSaveInstanceState(Bundle out) { public void onSaveInstanceState(Bundle out) {
super.onSaveInstanceState(out); super.onSaveInstanceState(out);
@ -121,8 +116,10 @@ public abstract class AbstractCalculatorPlotFragment extends CalculatorFragment
public void onResume() { public void onResume() {
super.onResume(); super.onResume();
plotData = Locator.getInstance().getPlotter().getPlotData();
createChart(plotData); createChart(plotData);
createGraphicalView(getView(), plotData); createGraphicalView(getView(), plotData);
getActivity().invalidateOptionsMenu();
} }
@Override @Override
@ -141,6 +138,8 @@ public abstract class AbstractCalculatorPlotFragment extends CalculatorFragment
getUiHandler().post(new Runnable() { getUiHandler().post(new Runnable() {
@Override @Override
public void run() { public void run() {
getActivity().invalidateOptionsMenu();
createChart(plotData); createChart(plotData);
final View view = getView(); final View view = getView();
@ -197,13 +196,14 @@ public abstract class AbstractCalculatorPlotFragment extends CalculatorFragment
*/ */
@Override @Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) { public void onCreateOptionsMenu(final Menu menu, MenuInflater inflater) {
super.onCreateOptionsMenu(menu, inflater); super.onCreateOptionsMenu(menu, inflater);
final List<IdentifiableMenuItem<MenuItem>> menuItems = new ArrayList<IdentifiableMenuItem<MenuItem>>(); final List<IdentifiableMenuItem<MenuItem>> menuItems = new ArrayList<IdentifiableMenuItem<MenuItem>>();
menuItems.add(PlotMenu.preferences); menuItems.add(PlotMenu.preferences);
if ( is3dPlotSupported() ) { menuItems.add(PlotMenu.functions);
menuItems.add(new IdentifiableMenuItem<MenuItem>() {
final IdentifiableMenuItem<MenuItem> plot3dMenuItem = new IdentifiableMenuItem<MenuItem>() {
@NotNull @NotNull
@Override @Override
public Integer getItemId() { public Integer getItemId() {
@ -214,9 +214,37 @@ public abstract class AbstractCalculatorPlotFragment extends CalculatorFragment
public void onClick(@NotNull MenuItem data, @NotNull Context context) { public void onClick(@NotNull MenuItem data, @NotNull Context context) {
Locator.getInstance().getPlotter().setPlot3d(true); Locator.getInstance().getPlotter().setPlot3d(true);
} }
}); };
menuItems.add(plot3dMenuItem);
final IdentifiableMenuItem<MenuItem> plot2dMenuItem = new IdentifiableMenuItem<MenuItem>() {
@NotNull
@Override
public Integer getItemId() {
return R.id.menu_plot_2d;
} }
fragmentMenu = ListActivityMenu.fromResource(R.menu.plot_menu, menuItems, SherlockMenuHelper.getInstance());
@Override
public void onClick(@NotNull MenuItem data, @NotNull Context context) {
Locator.getInstance().getPlotter().setPlot3d(false);
}
};
menuItems.add(plot2dMenuItem);
final boolean plot3dVisible = !plotData.isPlot3d() && is3dPlotSupported();
final boolean plot2dVisible = plotData.isPlot3d() && Locator.getInstance().getPlotter().is2dPlotPossible();
fragmentMenu = ListActivityMenu.fromResource(R.menu.plot_menu, menuItems, SherlockMenuHelper.getInstance(), new JPredicate<AMenuItem<MenuItem>>() {
@Override
public boolean apply(@Nullable AMenuItem<MenuItem> menuItem) {
if ( menuItem == plot3dMenuItem ) {
return !plot3dVisible;
} else if ( menuItem == plot2dMenuItem ) {
return !plot2dVisible;
}
return false;
}
});
final FragmentActivity activity = this.getActivity(); final FragmentActivity activity = this.getActivity();
if (activity != null) { if (activity != null) {
@ -251,6 +279,13 @@ public abstract class AbstractCalculatorPlotFragment extends CalculatorFragment
private static enum PlotMenu implements IdentifiableMenuItem<MenuItem> { private static enum PlotMenu implements IdentifiableMenuItem<MenuItem> {
functions(R.id.menu_plot_functions) {
@Override
public void onClick(@NotNull MenuItem data, @NotNull Context context) {
context.startActivity(new Intent(context, CalculatorPlotFunctionsActivity.class));
}
},
preferences(R.id.menu_plot_settings) { preferences(R.id.menu_plot_settings) {
@Override @Override
public void onClick(@NotNull MenuItem data, @NotNull Context context) { public void onClick(@NotNull MenuItem data, @NotNull Context context) {

View File

@ -0,0 +1,24 @@
package org.solovyev.android.calculator.plot;
import android.os.Bundle;
import com.actionbarsherlock.app.SherlockFragmentActivity;
import org.jetbrains.annotations.Nullable;
import org.solovyev.android.calculator.R;
import org.solovyev.android.fragments.FragmentUtils;
/**
* User: serso
* Date: 1/13/13
* Time: 5:05 PM
*/
public class CalculatorPlotFunctionsActivity extends SherlockFragmentActivity {
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.cpp_plot_functions_dialog);
FragmentUtils.createFragment(this, CalculatorPlotFunctionsFragment.class, R.id.dialog_layout, "plot-functions");
}
}

View File

@ -1,37 +0,0 @@
package org.solovyev.android.calculator.plot;
import org.jetbrains.annotations.NotNull;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
final class CalculatorPlotFunctionsController {
@NotNull
private static final CalculatorPlotFunctionsController instance = new CalculatorPlotFunctionsController();
@NotNull
private final List<XyFunction> functions = new ArrayList<XyFunction>();
private CalculatorPlotFunctionsController() {
}
@NotNull
public static CalculatorPlotFunctionsController getInstance() {
return instance;
}
@NotNull
public List<XyFunction> getFunctions() {
return Collections.unmodifiableList(functions);
}
public boolean addFunction(@NotNull XyFunction function) {
if (!functions.contains(function)) {
return functions.add(function);
} else {
return false;
}
}
}

View File

@ -4,6 +4,7 @@ import com.google.common.base.Function;
import com.google.common.collect.Lists; import com.google.common.collect.Lists;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import org.solovyev.android.calculator.CalculatorListFragment; import org.solovyev.android.calculator.CalculatorListFragment;
import org.solovyev.android.calculator.Locator;
import org.solovyev.android.calculator.about.CalculatorFragmentType; import org.solovyev.android.calculator.about.CalculatorFragmentType;
import org.solovyev.android.list.ListItemArrayAdapter; import org.solovyev.android.list.ListItemArrayAdapter;
@ -23,10 +24,11 @@ public class CalculatorPlotFunctionsFragment extends CalculatorListFragment {
public void onResume() { public void onResume() {
super.onResume(); super.onResume();
final List<ParcelablePlotInputListItem> items = Lists.transform(CalculatorPlotFunctionsController.getInstance().getFunctions(), new Function<XyFunction, ParcelablePlotInputListItem>() { final List<PlotFunctionListItem> items = Lists.transform(Locator.getInstance().getPlotter().getFunctions(), new Function<PlotFunction, PlotFunctionListItem>() {
@Override @Override
public ParcelablePlotInputListItem apply(@Nullable XyFunction input) { public PlotFunctionListItem apply(@Nullable PlotFunction input) {
return new ParcelablePlotInputListItem(input); assert input != null;
return new PlotFunctionListItem(input);
} }
}); });

View File

@ -26,11 +26,17 @@ public interface CalculatorPlotter {
boolean removeFunction(@NotNull PlotFunction plotFunction); boolean removeFunction(@NotNull PlotFunction plotFunction);
boolean removeFunction(@NotNull XyFunction xyFunction); boolean removeFunction(@NotNull XyFunction xyFunction);
void pin(@NotNull PlotFunction plotFunction); @NotNull
void unpin(@NotNull PlotFunction plotFunction); PlotFunction pin(@NotNull PlotFunction plotFunction);
void show(@NotNull PlotFunction plotFunction); @NotNull
void hide(@NotNull PlotFunction plotFunction); PlotFunction unpin(@NotNull PlotFunction plotFunction);
@NotNull
PlotFunction show(@NotNull PlotFunction plotFunction);
@NotNull
PlotFunction hide(@NotNull PlotFunction plotFunction);
void clearAllFunctions(); void clearAllFunctions();
@ -42,7 +48,9 @@ public interface CalculatorPlotter {
void plot(); void plot();
boolean isPlotPossible(@NotNull Generic expression); boolean is2dPlotPossible();
boolean isPlotPossibleFor(@NotNull Generic expression);
void setPlot3d(boolean plot3d); void setPlot3d(boolean plot3d);

View File

@ -31,6 +31,8 @@ public class CalculatorPlotterImpl implements CalculatorPlotter {
private boolean plotImag = false; private boolean plotImag = false;
private int arity = 0;
@NotNull @NotNull
private GraphLineColor realLineColor; private GraphLineColor realLineColor;
@ -134,6 +136,14 @@ public class CalculatorPlotterImpl implements CalculatorPlotter {
@Override @Override
public boolean updateFunction(@NotNull PlotFunction newFunction) { public boolean updateFunction(@NotNull PlotFunction newFunction) {
boolean changed = updateFunction0(newFunction);
if (changed) {
firePlotDataChangedEvent();
}
return changed;
}
public boolean updateFunction0(@NotNull PlotFunction newFunction) {
boolean changed = false; boolean changed = false;
synchronized (functions) { synchronized (functions) {
@ -156,26 +166,40 @@ public class CalculatorPlotterImpl implements CalculatorPlotter {
return removeFunction(new PlotFunction(xyFunction)); return removeFunction(new PlotFunction(xyFunction));
} }
@NotNull
@Override @Override
public void pin(@NotNull PlotFunction plotFunction) { public PlotFunction pin(@NotNull PlotFunction plotFunction) {
updateFunction(PlotFunction.pin(plotFunction)); final PlotFunction newFunction = PlotFunction.pin(plotFunction);
updateFunction0(newFunction);
return newFunction;
} }
@NotNull
@Override @Override
public void unpin(@NotNull PlotFunction plotFunction) { public PlotFunction unpin(@NotNull PlotFunction plotFunction) {
updateFunction(PlotFunction.unpin(plotFunction)); final PlotFunction newFunction = PlotFunction.unpin(plotFunction);
updateFunction0(newFunction);
return newFunction;
} }
@NotNull
@Override @Override
public void show(@NotNull PlotFunction plotFunction) { public PlotFunction show(@NotNull PlotFunction plotFunction) {
updateFunction(PlotFunction.visible(plotFunction)); final PlotFunction newFunction = PlotFunction.visible(plotFunction);
firePlotDataChangedEvent();
updateFunction(newFunction);
return newFunction;
} }
@NotNull
@Override @Override
public void hide(@NotNull PlotFunction plotFunction) { public PlotFunction hide(@NotNull PlotFunction plotFunction) {
updateFunction(PlotFunction.invisible(plotFunction)); final PlotFunction newFunction = PlotFunction.invisible(plotFunction);
firePlotDataChangedEvent();
updateFunction(newFunction);
return newFunction;
} }
@Override @Override
@ -203,6 +227,8 @@ public class CalculatorPlotterImpl implements CalculatorPlotter {
plot3d = false; plot3d = false;
} }
arity = maxArity;
firePlotDataChangedEvent(); firePlotDataChangedEvent();
} }
@ -233,7 +259,12 @@ public class CalculatorPlotterImpl implements CalculatorPlotter {
} }
@Override @Override
public boolean isPlotPossible(@NotNull Generic expression) { public boolean is2dPlotPossible() {
return arity < 2;
}
@Override
public boolean isPlotPossibleFor(@NotNull Generic expression) {
boolean result = false; boolean result = false;
int size = CalculatorUtils.getNotSystemConstants(expression).size(); int size = CalculatorUtils.getNotSystemConstants(expression).size();

View File

@ -42,27 +42,36 @@ public class PlotFunction {
} }
public static PlotFunction pin(@NotNull PlotFunction that) { public static PlotFunction pin(@NotNull PlotFunction that) {
return togglePinned(that, true);
}
@NotNull
public static PlotFunction togglePinned(@NotNull PlotFunction that, boolean pinned) {
final PlotFunction copy = that.copy(); final PlotFunction copy = that.copy();
copy.pinned = true; copy.pinned = pinned;
return copy; return copy;
} }
@NotNull
public static PlotFunction unpin(@NotNull PlotFunction that) { public static PlotFunction unpin(@NotNull PlotFunction that) {
final PlotFunction copy = that.copy(); return togglePinned(that, false);
copy.pinned = false;
return copy;
} }
@NotNull
public static PlotFunction visible(@NotNull PlotFunction that) { public static PlotFunction visible(@NotNull PlotFunction that) {
return toggleVisible(that, true);
}
@NotNull
public static PlotFunction toggleVisible(@NotNull PlotFunction that, boolean visible) {
final PlotFunction copy = that.copy(); final PlotFunction copy = that.copy();
copy.visible = true; copy.visible = visible;
return copy; return copy;
} }
@NotNull
public static PlotFunction invisible(@NotNull PlotFunction that) { public static PlotFunction invisible(@NotNull PlotFunction that) {
final PlotFunction copy = that.copy(); return toggleVisible(that, false);
copy.visible = false;
return copy;
} }
@NotNull @NotNull