[This post was last edited by eclipse at pm on 2002/09/03] Design Mode: actual MVC mode turbochen (original)
Keyword: design pattern, MVC, observer, Java
Content: 1. MVC 2. Observer Interface 3. Model 4. View 5. Controller 6. Run the program -------------------------------------------------------------------------------- MVC The Model-View-controller (MVC) structure is designed for applications that need to provide multiple views for the same data, it achieves the separation between the data layer and the presentation layer. Example: [Img] Quit We can see that several groups of data in the figure are displayed in different forms (views). One is a table style and the other is a graphic style. MVC divides such applications into three object types: Model: maintain data and provide data access methods. View: A Visual View of some or all data of the model. Controller: Process events. The following are typical MVC communication methods, [Img] http://www.javable.com/columns/serv_side/workshop/11/1.gif#/img] Events are handled by the controller. The controller receives user events and changes the model based on the event type. The view is registered in the model in advance. When the model data changes, each view that has been registered with the model is immediately notified. View get the latest data from the module and refresh yourself. To implement MVC, the most important part is to use the Observer Pattern in Design Pattern. The Observer mode allows an object to notify multiple observers when the observed object is modified ). The following describes how to use the Obserer mode to implement the MVC program structure. In my example, I want to show an example of student age. The age of each student is displayed in the form of a list and a graph. When the age changes, the display is automatically updated. Observer Interface To notify multiple observers when the observed object is modified, a small interface is usually required between the observer and the observer, as shown below: /* File: Observer. java */ Public interface Observer { Public void dataUpdate (Model model ); } This interface has a dataUpdate (Model model) method. Once this interface object is implemented, it becomes an observer. Model Create a data model. In my example, a data object is first created: /* File: Data. java */ Public class Data { Public int value; // student age Public String name; // Student name } Create a Model: /* File: Model. java */ Import java. util .*; Public class Model { ArrayList data = new ArrayList (); ArrayList observer = new ArrayList (); Public Model () {Super (); } Public Model (INT [] value, string [] Name) { For (INT I = 0; I <value. length; I ++ { Adddata (value [I], name [I]); } } Public Model (data [] data) { For (INT I = 0; I <data. length; I ++ { AddData (data [I]); } } Public void addData (int value, String name) { Data data = new Data (); Data. value = value; Data. name = name; This. data. add (data ); } Public void addData (Data data) { This. data. add (data ); } Public Data getData (int idx) { Return (Data) (data. get (idx )); } Public int size () { Return data. size (); } // Registers the observer with the model. Public void registerObserver (Observer o) { Observer. add (o ); } Public void removeObserver (Observer o) { Observer. remove (o ); } // When the data changes, the Controller calls this method to notify each Observer to refresh the view. Public void changeModel (Model model) { Data. clear (); For (int I = 0; I <model. size (); I ++ { This. addData (model. getData (I )); } DataUpdate (); } Private void dataupdate () { For (iterator I = observer. iterator (); I. hasnext (); { Observer o = (observer) (I. Next ()); O. dataupdate (this ); } } } This model provides various data access methods. And provides a changemodel method for the Controller to access. The registerobserver (Observer O) method is also provided to register the observer with the model. View We need to implement a list display style view 1 and a graphical view view2, and let them implement the observer interface, so that when the model data changes, automatically refresh yourself. /* File: View1.java */ Import javax. swing .*; Import java. awt .*; Import javax. swing. border .*; Public class View1 extends JPanel implements Observer { Model model; Public View1 () { } Public View1 (Model model) { Try { This. model = model; JbInit (); } Catch (exception E) { E. printstacktrace (); } } Private void jbinit () throws exception { This. setbackground (color. White ); This. setborder (New titledborder (borderfactory. createlineborder (color. Black, 1), "view1 "); } Public void paintcomponent (Graphics g) { Super. paintComponent (g ); If (model = null return; Int x = 20, y = 50; Int h = g. getFontMetrics (). getHeight (); For (int I = 0; I <model. size (); I ++ { Data data = model. getData (I ); G. drawString (data. name, x, y ); Y + = h; G. drawString (String. valueOf (data. value), x, y ); Y + = h; } } // When the model data changes, this method is automatically called to refresh the image Public void dataUpdate (Model model) { /** @ Todo: Implement this Observer method */ This. model = model; Repaint (); } } /* File: View2.java */ Import javax. swing .*; Import java. awt .*; Import javax. swing. border .*; Public class View2 extends JPanel implements Observer { Model model; Public View2 () { } Public View2 (Model model) { Try { This. model = model; JbInit (); } Catch (Exception e) { E. printStackTrace (); } } Private void jbInit () throws Exception { This. setBackground (Color. white ); This. setBorder (new TitledBorder (BorderFactory. createLineBorder (Color. black, 1), "View1 "); } Public void paintComponent (Graphics g) { Super. paintcomponent (g ); If (model = NULL return; Int x = 20, y = 50; Int H = G. getfontmetrics (). getheight (); Int width = This. getwidth (); Int Height = This. getheight (); Int Sy = height/model. Size (); Int SX = width/2; For (int I = 0; I <model. size (); I ++ { Data data = model. getData (I ); Int value = data. value; Int dx = 3; Int r = 3; Color c = new Color (int) (255 * Math. random (), (int) (255 * Math. random (), (int) (255 * Math. random ())); Int cx = sx; Int cy = y + I * sy; For (int j = 0; j <value; j ++ { G. setColor (c ); G. drawOval (cx, cy, r, r ); R + = dx; } G. drawString (data. name, 25, cy ); } } // When the model data changes, this method is automatically called to refresh the image Public void dataUpdate (Model model) { /** @ Todo: Implement this Observer method */ This. model = model; Repaint (); } } Controller All right, the Model and Observer in MVC are all set up. Let's finally make a Controller: Import java. awt .*; Import javax. swing .*; Import javax. Swing. Border .*; Import java. AWT. event .*; Public class controller extends jframe { Model = new model (); View1 view1 = new view1 (model ); View2 view2 = new view2 (model ); Jscrollpane jscrollpane1 = new jscrollpane (); Jbutton jbutton1 = new jbutton (); Jtextfield jtextfield1 = new jtextfield (); Jtextfield jtextfield2 = new jtextfield (); Jlabel jlabel1 = new jlabel (); JLabel jLabel2 = new JLabel (); JLabel jLabel3 = new JLabel (); Public Controller () { Try { JbInit (); } Catch (Exception e) { E. printStackTrace (); } } Private void jbInit () throws Exception { Data [] data = new Data [2]; Data [0] = new Data (); Data [1] = new Data (); Data [0]. name = "Ted "; Data [0]. value = 20; Data [1]. name = "Joy "; Data [1]. value = 14; Model. addData (data [0]); Model. addData (data [1]); // Note the following two lines: register its observer View1 and View2. Model. registerObserver (view1 ); Model. registerObserver (view2 ); This. getContentPane (). setLayout (null ); JScrollPane1.setBounds (new Rectangle (0, 0, 3, 3 )); JButton1.setBounds (new Rectangle (309,259,101, 27 )); JButton1.setText ("Update "; JButton1.addActionListener (new java. awt. event. ActionListener () { Public void actionreceivmed (ActionEvent e) { Jbutton?action=med (e ); } }); JTextField1.setText ("20 "; JTextField1.setBounds (new Rectangle (80,254, 52, 30 )); JTextField2.setText ("14 "; Jtextfield2.setbounds (New rectangle (178,255, 50, 31 )); Jlabel1.settext ("Age :"; Jlabel1.setbounds (New rectangle (41,226, 47, 23 )); Jlabel2.settext ("Ted "; Jlabel2.setbounds (New rectangle (42,252, 35, 33 )); Jlabel3.settext ("Joy "; Jlabel3.setbounds (New rectangle (144,255, 31, 31 )); View1.setbounds (New rectangle (7, 5,225, 20 ); View2.setBounds (new Rectangle (234, 4,219,209 )); This. getContentPane (). add (jScrollPane1, null ); This. getContentPane (). add (jTextField2, null ); This. getContentPane (). add (jTextField1, null ); This. getContentPane (). add (jLabel2, null ); This. getContentPane (). add (jLabel3, null ); This. getContentPane (). add (jLabel1, null ); This. getContentPane (). add (jButton1, null ); This. getContentPane (). add (view1, null ); This. getContentPane (). add (view2, null ); } // Press the Update button to notify the Model data to change. Void jbutton?action=med (ActionEvent e) { Data [] data = new Data [2]; Data [0] = new Data (); Data [1] = new Data (); Data [0]. name = jLabel1.getText (); Data [0]. value = integer. parseint (jtextfield1.gettext ()); Data [1]. Name = jlabel2.gettext (); Data [1]. value = integer. parseint (jtextfield2.gettext ()); Model M = new model (data ); This. model. changemodel (m ); } Public static void main (string [] ARGs) { Controller c = new controller (); C. setsize (475,310 ); C. setVisible (true ); } } Run the program You can save these codes as the corresponding source files and execute the following command to compile Javac Controller. java Run Java Controller. class You can see the effect of program execution, You can try to change the age of two students and click the Update button to Update the view. How can we experience the convenience brought by the MVC structure to the program ?; |